Title photo
frugal technology, simple living and guerrilla large-appliance repair
Thu, 09 Nov 2017

Overcoming a permission error while using Ruby to move files

I'm not sure if this is a Windows-specific problem (I am currently developing on Windows 10), but part of the Ruby script in my Blog Poster app allows the user to "archive" all of the text files created as blog/social posts by moving them from the main program directory to an archives directory. I could opt not to create files at all, or have the script continue to overwrite the same one for each post.

But for now I'm keeping all of the text files (which the script creates and names based on the <title> tag of URLs that are part of the post, and I have an option to move those text files to the archive directory:

Dir.glob("*.txt") {|f| FileUtils.move File.expand_path(f), "archive" }

This part of the Ruby script worked fine when I started it and was doing nothing else, but if I used it to create one or more files, invoking the "archive" feature would error out and kill the script, saying that there was a permission issue.

Laziness. I looked in Stack Overflow and found the solution, which consisted of adding :force => true to the expression:

Dir.glob("*.txt") {|f| FileUtils.move File.expand_path(f), "archive", :force => true }

Now I can create posts (and their matching .txt files, which my blog uses) and then archive them at any point without the permission error killing the script. Thanks, Stack Overflow user mudasobwa.

Update: This modification allowed the script to keep running, but any files created during the current session are NOT moved to the archive directory.

The reason the files created during the session were not deletable is due to the script reading them out in the console. I will figure out a way to provide this output without rendering the files "undeletable" via Ruby.

Here are the lines I am removing for now:

puts "This is your file:\n\n"
File.open( @yourFileName ).each do |line|
   puts line
end
Mon, 23 Oct 2017

The Ruby Terminal Apps Toolkit could solve many problems

I'm not quite sure how I stumbled upon the Ruby Terminal Apps Toolkit, but the gems included can definitely speed your development of interactive Ruby apps on the command line.

I just coded a menu for my app, and these gems by Piotr Murach offer a lot of ways to do this easily and to solicit and process user input.

The next thing I'm looking at doing in my app is allowing users to open lines for editing in their text editor of choice, and these TTY gems definitely do that. I wasn't thinking that shelling out to an editor would be so hard (meaning that was something that Ruby can do with no gems), but maybe this is a better (or easier) way.

The "hard" part in allowing user editing in my app is that I am assembling files to upload from a series of variables, and I think I'll have to create temporary files for editing that only include the component being modified (i.e. title, text, link, filename) because my app knows how to turn variables into a file but not a file into a series of variables, though that is something I could code into it. (But I may not do this because I am thinking of going in another direction and not creating actual files on the system at all and using Ruby to stream the data via FTP.)

That's more detail without context about the app I'm working on than you need.

tl;dr: The Ruby Terminal Apps Toolkit can speed up development of command-line based apps. You can use single gems or the whole thing. It's up to you.

Sat, 21 Oct 2017

My blog-posting program in Ruby

I'm actually doing it. I'm writing a blog-posting program that will take an http link, extract the remote page's title and create a social-media-style blog post (title, body text and link) that can be easily uploaded to my flat-file blogging system's server.

The idea is to make it as easy to post a "social"-style update to my own blog as it is to post to Twitter (or Facebook or Google+).

(I use IFTTT -- and formerly dlvr.it -- to post these social entries on Twitter, but I could see this program taking over that task as well.)

Back to my application. I could have gone several different ways from a conceptual standpoint.

  • I could have done this idea as a web app, but in order to get the files to upload to the blog, I'd either have to write a server component on that side, or create a backend service -- with some measure of security -- to handle the upload (I'm using FTP, but it doesn't have to be that).

  • I thought about a desktop GUI. I want this to be a true cross-platform app. I seriously considered using the now-ancient Tk framework with Ruby. I less-seriously considered Java FX, though I did successfully hack together code to upload via FTP using Java. (At least it was a worthwhile programming exercise.) I could have gone with QT. Maybe I could have done the whole thing with QML.

I'm not ruling out any of these GUI solutions, but I needed to start coding, and the easiest, quickest thing for me to do (or so I thought) is a menu-driven console app. I could have gone with Java, JavaScript, Ruby, even Perl. I did tests of various components in three of those languages.

I'm writing the app for the console with an eye toward re-using the code in a future GUI app, and for that reason maybe I should have used JavaScript.

But I really wanted to use Ruby. I'm trying to grasp object-orientated programming, and there is a whole lot of web-based help for Ruby programmers that often acknowledges that there are beginners out there who need a helping hand.

And I really would love to eventually port this code to Tk, or even as a Sinatra or Rails app. I should want to do it in JavaScript. But Ruby is so friendly, and it's made for use in the console.

So I'm writing it in Ruby. And I have some 190 lines of code that do the following:

  • Display a menu of tasks and wait for input
  • When a URL is entered, grab the HTML title
  • Create a simple document with a title and text derived from the remote HTML title
  • Add a Markdown-formatted link back to the original HTML page
  • Save all as a text file with an auto-generated file name incorporating the current date and text derived from the title
  • Allow user to enter different text for the title or body
  • Let user choose not to include the source site's URL
  • Save all to a text file
  • Upload to website via FTP and "tell" blog to index the new entry

I have all of these features working, and while the app is very far from perfect, it is functional. The code isn't ready for public consumption -- it needs lots of cleanup before I publish it, and it's really meant more for Ode users and blogs that work in a similar way (files are uploaded to a server, from which the blog software renders them for the reader) than it is for flat-file systems such as Hugo, where a dedicated program builds the blog locally and sends files on their way, but the concepts and code used in this app can certainly be modified for that workflow -- and I'm not at all above doing that in the future.

Aside from adding more features, primarily the ability to edit elements instead of re-typing them (maybe by invoking the vi editor), I want to make the code more modular. Right how it's a huge procedural hack, and modularity (and object orientation) will make it cleaner and more flexible. That's the idea anyway.

Before that I need to clean up the configuration, which is all over the place.

Still, I wanted to make an app, I used the skills I had (and Googled and read plenty), and now I have something that works, however ugly it may look on the back end.

Sat, 08 Jul 2017

'Learn Ruby on Rails' by Daniel Kehoe updated for Rails 5.1

'Learn Ruby on Rails' by Daniel Kehoe has been updated for Rails 5.1.

Wed, 30 Nov 2016

Basic operations for arrays in Ruby

From Solid Foundation Web Development: Basic operations for arrays in Ruby

Mon, 12 Sep 2016

Using Dir.glob to delete files with a pattern in Ruby

I have a bunch of files in a directory, and I want to delete all that begin their filename with the letters X16 (e.g. X16data.xml)

I used Dir.glob to select the files and iterated over what comes up in the pattern, using File.delete to get rid of what I don't want (Thanks, Stack Overflow):

Dir.glob("X16*") do |file|
 File.delete(file)
end

You can put any kind of regex in here, and it'll probably work. That's the theory anyway.

Sat, 10 Sep 2016

The rubyzip gem for creating and opening archives

On my current project, I am trying to use using rubyzip to unzip an archive.

So far it's not working, and I'll probably shell out to Bash and Linux/Unix's unzip to get it done.

I figured it out. Now I have to manage the unzipped files (deleting the unused, renaming the good, then deleting the good at the beginning of the run) and account for NOT running the program if there is no file on the other end.

Thu, 16 Jun 2016

The Bastards Book of Ruby

While it calls itself out as old and out of date, I really like The Bastards Book of Ruby.

I recognize that Ruby is no longer the new hotness, but it's still so useful and, dare I say, user-friendly. For those reasons, I'd love to see updated versions of just about every book out there.

I'm using the old (as the hills) "Learning Ruby" by Michael Fitzgerald (2007, O'Reilly), The Pickaxe book ("Programming Ruby") from Ruby version 1.9.2 (2010/11, Pragmatic Programmers, though do I realize there is a 2013 edition).

The beginners books seem to be the oldest. At my level, everything seems to be working, so I will maybe complain a little less.

I do have a Rails book, "Rails Crash Course," by Anthony Lewis, that's much newer, but I'm not there quite yet. And there's always Michael Hartl's "The Ruby on Rails Tutorial", of which the more I see, the more I like.

Using Ruby to delete blocks of text across multiple lines

I tend to learn things in programming when I have a problem to solve. This is just such a case.

I was working with a huge XML file, and I needed to trim elements out of it that begin with <generic tag> and end with </generic tag>, and include a random amount of text and other tags, across multiple lines, in between.

At first I tried using the Nokogiri gem, but it just wasn't happening. I was working on my Election Results script, and ... the election -- they hold it on a certain date, you know.

I would have to brute-force it. Like I always do.

My whole idea this cycle was to dump my giant sed hack from elections past and use mostly (if not all) Ruby to parse the XML I get from the state of California and provide the JSON output my fellow dev needed for the front end. (I also have a ton of fixed-width ASCII from Los Angeles County to deal with, as well as scraped HTML from San Bernardino County, but those are other tales for other times.)

With the state data, I had the XML-to-JSON conversion covered with Ruby's Crack gem. But I just couldn't pare down the XML to make the JSON a manageable size.

Read the rest of this post

Wed, 15 Jun 2016

A great Ruby loops tutorial from Prograils

A company called Prograils offers a great tutorial, Loops in Ruby - all possible approaches.

It looks like a good reference for when you're writing a Ruby program and need to figure out which kind of loop will work best in a particular situation.