I put together a list of macOS processes in a spreadsheet and wrote a short script to turn that into HTML. My intention was to update the spreadsheet whenever I found new information and then automatically update the blog. My small script was only useful to create HTML to manually place on a blog page. And the spreadsheet had more information then I could reasonably display in a simple table.

What I really wanted was to create a page per process. Luckily, WordPress was built with XML-RPC interfaces that could solve this problem.

The resulting script works by first generating and setting the contents of the main process page. The page was initially created before the script was run. After the main process page is updated, the script then starts creating a page for each individual process. If a process page already exists, then the page’s contents are updated.

First, we setup the XML-RPC client:

blog = XMLRPC::Client.new3(:host => "tedwise.com", :path => "/xmlrpc.php")

Then we pull down a list of all the pages:

pages = blog.call("wp.getPages", 1, USERID, PASSWORD, 1000)

The wp.getPages call only returns a maximum of 10 pages. The WordPress documentation doesn’t mention it, but the wp.getPages call takes an optional third parameter that raises that maximum. In the above example, I raise the maximum to 1000. The ‘pages’ object holds the full description of all the pages in the WordPress blog.

I locate the main page with a simple bit of Ruby:

page = pages.find {|p| p['title'] == 'macOS Processes'}

Then generate the contents of the page from the spreadsheet CSV file and update the page.

blog.call("wp.editPage", 0, page['page_id'], USERID, PASSWORD, {:wp_page_parent_id => page['wp_page_parent_id'], :wp_slug => page['wp_slug'], :title => page['title'], :description => content, :categories => page['categories'], :mt_allow_comments => 0, :mt_allow_pings => 0}, true)

Most of the parameters to the wp.editPage call come from the information pulled down from WordPress in the wp.getPages call.

Each process entry in the spreadsheet is checked against the list of pre-existing pages. If the page doesn’t exist, we generate a WordPress slug:

def slugify(title)
  title.downcase.gsub(/[ \._]/, '-')

After the slug is generated, we create the WordPress page.

blog.call("wp.newPage", 0, USERID, PASSWORD, {:wp_page_parent_id => parent_id, :wp_slug => slug, :title => title, :description => content, :categories => ["Mac"], :mt_allow_comments => 0, :mt_allow_pings => 0}, true)

If the page does exist, it gets updated using the same call as the main page. The whole script is available here.

BTW, the eBook ‘Digging Into Wordpress’ has helped me understand Wordpress development.