Ramblings of a software tester…developer…tester…

Ramblings of a tester who is a programmer who is a tester who is a developer…

Packer 0.8.1.

Previously I wrote that the scripts I’m writing, are failing because Packer hangs.

Apparently, this was a known issue. And apparently, I was using an older version, 0.7.5. After I updated everything is working wonderfully!!!

And for my thanks, here is an updated PowerShell script for provisioning my dotnet stuff.

$source = "http://download.microsoft.com/download/1/6/7/167F0D79-9317-48AE-AEDB-17120579F8E2/NDP451-KB2858728-x86-x64-AllOS-ENU.exe"
$destination = "C:\Windows\Temp\dotnet.exe"
Write-Host 'Starting to download dotnet file.'
try {
  (New-Object System.Net.WebClient).DownloadFile($source, $destination)
} catch [Exception] {
  Write-Host "Exception during download. Probable cause could be that the directory or the file didn't exist."
  Write-Host '$_.Exception is' $_.Exception
}
Write-Host 'Download done. Checking if file exists.'
if (!(Test-Path $destination)) {
  Write-Host 'Downloading dotnet Failed!'
} else {
  Write-Host 'Download successful.'
}
 
Write-Host 'Starting install process.'
try {
  Start-Process -FilePath $source -ArgumentList "/q /norestart" -Wait -PassThru
} catch [Exception] {
  Write-Host 'Exception during install process.'
  Write-Host '$_.Exception is' $_.Exception
}
 
Write-Host 'All done. Goodbye.'

Thanks for reading!
Gergely.

Powershell can also be nice -Or Installing Java silently and waiting

Hello folks.

Today, I would like to show you a small script. It installs Java JDK, both version, x86 and 64 bit, silently, and wait for that process to finish.

The wait is necessary because /s on a java install has the nasty habit of running in the background. If you are using a .bat file, you shouldn’t, than you would use something like: start /w jdk-setup.exe /s. This gets it done, but is ugly. Also, if you are using Packer and PowerShell provisioning, you might want to set up some environment variables as well for the next script. And you want that property to be available and you don’t want to mess it up with setting a path into a file and then re-setting your path on the begin of your other script. Or pass it around with Packer. No. Use a proper PowerShell script. Learn it. It’s not that hard. Be a professional. Don’t hack something together for the next person to suffer at.

Here is how I did it. Hope it helps somebody out.

$JDK_VER="7u75"
$JDK_FULL_VER="7u75-b13"
$JDK_PATH="1.7.0_75"
$source86 = "http://download.oracle.com/otn-pub/java/jdk/$JDK_FULL_VER/jdk-$JDK_VER-windows-i586.exe"
$source64 = "http://download.oracle.com/otn-pub/java/jdk/$JDK_FULL_VER/jdk-$JDK_VER-windows-x64.exe"
$destination86 = "C:\vagrant\$JDK_VER-x86.exe"
$destination64 = "C:\vagrant\$JDK_VER-x64.exe"
$client = new-object System.Net.WebClient
$cookie = "oraclelicense=accept-securebackup-cookie"
$client.Headers.Add([System.Net.HttpRequestHeader]::Cookie, $cookie)
 
Write-Host 'Checking if Java is already installed'
if ((Test-Path "c:\Program Files (x86)\Java") -Or (Test-Path "c:\Program Files\Java")) {
    Write-Host 'No need to Install Java'
    Exit
}
 
Write-Host 'Downloading x86 to $destination86'
 
$client.downloadFile($source86, $destination86)
if (!(Test-Path $destination86)) {
    Write-Host "Downloading $destination86 failed"
    Exit
}
Write-Host 'Downloading x64 to $destination64'
 
$client.downloadFile($source64, $destination64)
if (!(Test-Path $destination64)) {
    Write-Host "Downloading $destination64 failed"
    Exit
}
 
 
try {
    Write-Host 'Installing JDK-x64'
    $proc1 = Start-Process -FilePath "$destination64" -ArgumentList "/s REBOOT=ReallySuppress" -Wait -PassThru
    $proc1.waitForExit()
    Write-Host 'Installation Done.'
 
    Write-Host 'Installing JDK-x86'
    $proc2 = Start-Process -FilePath "$destination86" -ArgumentList "/s REBOOT=ReallySuppress" -Wait -PassThru
    $proc2.waitForExit()
    Write-Host 'Installtion Done.'
} catch [exception] {
    write-host '$_ is' $_
    write-host '$_.GetType().FullName is' $_.GetType().FullName
    write-host '$_.Exception is' $_.Exception
    write-host '$_.Exception.GetType().FullName is' $_.Exception.GetType().FullName
    write-host '$_.Exception.Message is' $_.Exception.Message
}
 
if ((Test-Path "c:\Program Files (x86)\Java") -Or (Test-Path "c:\Program Files\Java")) {
    Write-Host 'Java installed successfully.'
}
Write-Host 'Setting up Path variables.'
[System.Environment]::SetEnvironmentVariable("JAVA_HOME", "c:\Program Files (x86)\Java\jdk$JDK_PATH", "Machine")
[System.Environment]::SetEnvironmentVariable("PATH", $Env:Path + ";c:\Program Files (x86)\Java\jdk$JDK_PATH\bin", "Machine")
Write-Host 'Done. Goodbye.'

Now, there is room for improvement here. Like checking exit code, doing something extra after a failed exit. Throwing an exception, and so on and so forth. But this is a much needed improvement from calling a BAT file.

And you would use this in a Packer JSON file like this..

{
      "type": "powershell",
      "scripts": [
        "./scripts/jdk_inst.ps1"
      ]
}

Easy. And at the end, the System.Environment actually writes out into the registry permanently so no need to pass it around in a file or something ugly like that.

Hope this helps somebody.
Thanks for reading.
Gergely.

Setting up a new Laptop with Puppet

Hello folks.

So, some of you know puppet, some of you don’t. Puppet is a configuration management system. It’s quite awesome. I like working with it. One of the benefits of puppet is, that I never, ever, EVER have to setup a new laptop from scratch, EVER again.

I’m writing a puppet manifest file which sets up my new laptop to my liking. I will improve it as I go along. Here is version 1.0.

# include apt
 
class base::basics {
        $packages = ['git', 'subversion', 'mc', 'vim', 'maven', 'gradle']
 
        exec { "update":
                command => "/usr/bin/apt-get update",
        }
 
        package { $packages:
                ensure => installed,
                require => Exec["update"],
        }
 
}
 
class base::skype {
        exec { "add-arc":
                command => "/usr/bin/dpkg --add-architecture i386",
        }
 
        exec { "add-repo-skype":
                command => "/usr/bin/add-apt-repository \"deb http://archive.canonical.com/ \$(lsb_release -sc) partner\"",
                require => Exec['add-arc'],
        }
 
        exec { "update-and-install":
                command => "/usr/bin/apt-get update && /usr/bin/apt-get install skype",
                require => Exec['add-repo-skype'],
        }
}
 
class base::java8 {
        # Automatically does an update afterwards
        # apt::ppa { 'ppa:webupd8team/java': }
        exec { "add-repo-java":
                command => "/usr/bin/add-apt-repository -y \"ppa:webupd8team/java\" && /usr/bin/apt-get update"
        }
 
        exec { "set-accept":
                command => "/bin/echo /usr/bin/debconf shared/accepted-oracle-license-v1-1 select true | sudo /usr/bin/debconf-set-selections && /bin/echo /usr/bin/debconf shared/accepted-oracle-license-v1-1 seen true | sudo /usr/bin/debconf-set-selections",
                require => Exec['add-repo-java'],
        }
 
        exec { "install":
                command => "/usr/bin/apt-get install -y oracle-java8-installer",
                require => Exec['set-accept'],
        }
 
        exec { "setup_home":
                command => "/bin/echo \"export JDK18_HOME=/usr/lib/jvm/java-8-oracle/\" >> /etc/environment",
                require => Exec['install'],
        }
}
 
include base::basics
include base::skype
include base::java8

I’ll improve upon it as I go, and you can check it out later from my git repo. I removed the parts which required extra libraries for now, as I want it to run without the need of getting extra stuff installed. I might automate that part as well later on.

EDIT: https://github.com/Skarlso/puppet/blob/master/manifests/base_setup.pp

Have fun.
Gergely.

Busy building the future

Fact is, I’ve been busy.

I’ve got a new job as a build engineer. As sort of a devops kind of guy. It’s extremely interesting considering that I made a career as a tester. Granted, I always was technical, and never really knew my path; but it seems my path is finding me after all.

In the past years, I got better at Docker, Puppet, Chef, AWS, Packer, Vagrant, Gradle, and a hell of a lot more. Also honed my linux skills from the ability of doing an ls -l to do an find . -type f -atime +5 | xargs rm -fr (find all the files which are 5 days older and pipe them to a delete command). I already read many books about devops but this time, it’s different. This time, I can actually do these things as well in a live environment.

As once a friend of mine told me: “You ain’t gonna learn anything unless you are getting payed for it.” Wise words. True words.

So stayed tuned for some devops and engineering type posts. I would like to continue working on the Django parts as well, however given my priorities and lack of time ( family and stuff, must choose what I learned in the hour I get each day), it might fall behind. I might stick it into some kind of provision practice or even give it a Travis.ci and put it into a gradle project. Now THAT’S interesting.

Cheers folks.
And as always,
Thanks for reading.
Gergely.

Django – RPG – Part 3

Hello folks.

A small update to this. I created the model now, which is the database design for this app. It’s very simple, nothing fancy. Also, I’m writing the app with Python 3 from now on.

Here is the model now:

from django.db import models
from django.contrib.auth.models import User
 
# Create your models here.
 
 
class Item(models.Model):
    name = models.CharField(max_length=100, default="Item")
    damage = models.IntegerField(default=0)
    defense = models.IntegerField(default=0)
    consumable = models.BooleanField(default=False)
 
    def __str__(self):
        return self.name
 
 
class Inventory(models.Model):
    items = models.ManyToManyField(Item)
 
    def __str__(self):
        return self.items
 
 
class Character(models.Model):
    # By default Django uses the primery key of the related object.
    # Hence, no need to specify User.id.
    user = models.OneToOneField(User, null=True)
    name = models.CharField(max_length=100)
    inventory = models.ForeignKey(Inventory)
 
    def __str__(self):
        return self.name

Worth noting a few things here. The __str__ is only with Python 3. In Python 2 it would be unicode. And the OneToOne and the foreign key are automatically using Primary keys defined in the references model. The __str__ is there to return some view when you are debugging in the console instead of [<Item: Item object>].

In order to apply this change you just have to run this commend (given you set up your app in the settings.py as an INSTALLED_APP):

python manage.py makemigrations polls

This creates the migration script. And this applies it:

python manage.py migrate

I love the fact that django creates incremental migration scripts out of the box. So if there was any problem at all, you can always roll back. Which comes very handy in certain situations.

That’s it.

Thanks for reading!
Gergely.

Small Python GUI to Calculate Lever Distance

Hi folks.

Just a small script which calculates your distance from a lever focal point if you know your weight, the object’s weight and the object’s and the distance the object has from the focal point of the lever.

Like this:

slide0001_image007

This script will give you D1. And this is how it will look like in doing so:

Screen Shot 2015-04-10 at 15.03.02

So, in order for me (77kg) to lift an object of 80kg which is on a, by default, 1 meter long lever, I have to stand back ~1.03meters. Which is totally cool, right?

Here is the code:

from Tkinter import *
import ttk
 
def calculate(*args):
    try:
        your_weight_value = float(your_weight.get())
        object_weight_value = float(object_weight.get())
        object_distance_value = float(object_distance.get())
        your_distance.set((object_weight_value * object_distance_value) / your_weight_value)
    except ValueError:
        pass
 
root = Tk()
root.title("Lever distance counter")
 
mainframe = ttk.Frame(root, padding="4 4 12 12")
mainframe.grid(column=0, row=0, sticky=(N, W, E, S))
mainframe.columnconfigure(0, weight=1)
mainframe.rowconfigure(0, weight=1)
 
your_weight = StringVar()
object_weight = StringVar()
object_distance = StringVar()
your_distance = StringVar()
 
object_distance.set("1")
 
your_weight_entry = ttk.Entry(mainframe, width=7, textvariable=your_weight)
your_weight_entry.grid(column=2, row=1, sticky=(W, E))
object_weight_entry = ttk.Entry(mainframe, width=7, textvariable=object_weight)
object_weight_entry.grid(column=2, row=2, sticky=(W, E))
object_distance_entry = ttk.Entry(mainframe, width=7, textvariable=object_distance)
object_distance_entry.grid(column=2, row=4, sticky=(W, E))
 
 
ttk.Label(mainframe, textvariable=your_distance).grid(column=2, row=3, sticky=(W, E))
ttk.Label(mainframe, text="Your weight").grid(column=1, row=1, sticky=W)
ttk.Label(mainframe, text="Object weight").grid(column=1, row=2, sticky=W)
ttk.Label(mainframe, text="Object Distance").grid(column=1, row=3, sticky=W)
ttk.Label(mainframe, text="Your Distance").grid(column=1, row=4, sticky=W)
 
ttk.Label(mainframe, text="kg").grid(column=3, row=1, sticky=W)
ttk.Label(mainframe, text="kg").grid(column=3, row=2, sticky=W)
ttk.Label(mainframe, text="m").grid(column=3, row=3, sticky=W)
ttk.Label(mainframe, text="m").grid(column=3, row=4, sticky=W)
 
ttk.Button(mainframe, text="Calculate", command=calculate).grid(column=3, row=5, sticky=W)
 
for child in mainframe.winfo_children(): child.grid_configure(padx=5, pady=5)
 
your_weight_entry.focus()
root.bind('', calculate)
 
root.mainloop()

Please enjoy, and feel free to alter in any way. I’m using Tkinter and a grid layout which I find very easy to work with.

Thanks for reading,
Gergely.