Lua wurde 1993 von der Computer Graphics Technology Group der Päpstlichen Katholischen Universität von Rio de Janeiro in Brasilien entwickelt. Lua ist freie Software und wurde bis zur Version 4 unter einer eigenen BSD-Lizenz veröffentlicht, seit Version 5 unter der MIT-Lizenz.
Lua kann sowohl zur Erstellung eigenständiger Programme verwendet werden als auch als eingebettete Sprache dienen.
local parameter = "root"; print("Parameter: ", parameter) local pfaddatei = ("/usr/bin/id " .. parameter) print("Kammando: ", pfaddatei) datei = assert (io.popen (pfaddatei)) print ("Temp-Datei-Händler: ", datei) ausgabe = datei:read ("*l") -- read one line print ("Rückgabewert: ", ausgabe) for line in io.lines(pfaddatei) do print (line) end local myFile = io.open( pfaddatei, "r+b" ) dateigroesse = (myFile:seek("end")) print ("die Datei ist so groß: " .. dateigroesse)
> lua lua_start.lua Parameter: root Kammando: /usr/bin/id root Temp-Datei-Händler: file (0x1657270) Rückgabewert: uid=0(root) gid=0(root) groups=0(root)
print('eigener Skriptname wird ausgegeben:') print(arg[0]) print() print('erstes Argument wird ausgegeben:') print(arg[1]) print() print('alle Argumente werden ausgegeben:') print(...)
Beispiel:
> lua /tmp/test_args.lua 0 1 2 3 4 eigener Skriptname wird ausgegeben: /tmp/test.lua erstes Argument wird ausgegeben: 0 alle Argumente werden ausgegeben: 0 1 2 3 4
env:connect(sourcename[,username[,password[,hostname[,port]]]])conn:escape(str)conn:getlastautoid()cur:numrows()local dbConf = {} dbConf.database = 'mitglieder' dbConf.username = 'fritz' dbConf.passwort = 'geheim' dbConf.hostname = '10.234.123.45' dbConf.port = "3306" require("mime") luasql = require("luasql.mysql") local env = assert(luasql.mysql()) local con = assert(env:connect ( dbConf.database, dbConf.username, dbConf.passwort, dbConf.hostname, dbConf.port )) function rows (connection, sql_statement) local cursor = assert (connection:execute (sql_statement)) return function () return cursor:fetch() end end for id, name, address in rows (con, "select * from dealer_logins") do -- "id" und "name" sind Spaltennamen in der Tabelle print (string.format ("%s: %s", id, name)) end con:close() env:close()
ausführen
> lua /tmp/test_db.lua
Voraussetzungen:
$HTTP["host"] =~ "10.10.69.69" { magnet.attract-physical-path-to = ( "/etc/lighttpd/test.lua" ) }
datei = io.open("/tmp/lua_env.txt","w") datei:write("uri.authority: ", string.format('%s', lighty.env["uri.authority"]), "\n") datei:write("uri.path: ", string.format('%s', lighty.env["uri.path"]), "\n") datei:write("uri.path-raw: ", string.format('%s', lighty.env["uri.path-raw"]), "\n") datei:write("uri.scheme: ", string.format('%s', lighty.env["uri.scheme"]), "\n") datei:write("physical.path: ", string.format('%s', lighty.env["physical.path"]), "\n") datei:write("physical.rel-path: ", string.format('%s', lighty.env["physical.rel-path"]), "\n") datei:write("physical.doc-root: ", string.format('%s', lighty.env["physical.doc-root"]), "\n") datei:close()
> cat /tmp/lua_env.txt uri.authority: 10.123.234.56 uri.path: /test.php uri.path-raw: /test.php uri.scheme: https physical.path: /var/www/test.php physical.rel-path: /test.php physical.doc-root: /var/www/
Leider gibt es für LighttpD kein Modul um die Passwortabfrage auf eine DB zu realisieren, wie man es vom Apache kennt. Um eine derartige Funktionalität in LighttpD umzusetzten, muss man ein entsprechendes LUA-Skript einbinden.
Die Dateien, die Passwörter enthalten, dürfen nicht für die Welt lesbar sein!
> chown 33:33 /etc/lighttpd/sha512crypt.php /etc/lighttpd/mysql_auth.lua > chmod 0640 /etc/lighttpd/sha512crypt.php /etc/lighttpd/mysql_auth.lua
Die individuellen Daten sehen wie folgt aus, sie können (und müssen) den persönlichen Gegebenheiten angepasst werden:
10.10.69.6910.123.45.673306pwdbpwtabname und passwortSHA512tuqu7Cua_ox1jieW# bei Zugriffen auf diesen Web-Server soll das LUA-Skript aktiviert werden
$HTTP["host"] =~ "10.10.69.69" {
magnet.attract-physical-path-to = ( "/etc/lighttpd/mysql_auth.lua" )
}
-- nur "/geheim.php" soll passwortgeschützt sein if ( string.format('%s', lighty.env["uri.path"]) == "/geheim.php" ) then -- Passwörter dürfen nur per https eingegeben werden if (lighty.env["uri.scheme"] == "http") then lighty.header["Location"] = "https://" .. lighty.env["uri.authority"] .. lighty.env["request.uri"] return 302 end --[[ Config Variables ]] local dbConf = {} dbConf.database = 'pwdb' dbConf.username = 'fritz' dbConf.passwort = 'geheim' dbConf.hostname = '10.123.45.67' dbConf.port = "3306" --[[ Requires ]] -- Debian package: liblua5.1-socket2 -- required for Base64 De-/encoding. See: http://w3.impa.br/~diego/software/luasocket/home.html require("mime") -- Debian package: liblua5.1-sql-mysql-2 -- Lua Mysql Driver luasql = require("luasql.mysql") --[[ Function to send HTTP-Auth request ]] function doAuth() lighty.header["WWW-Authenticate"] = string.format('Basic realm="%s"', lighty.env["uri.authority"]) return 401 end --[[ Function to check Auth Creds against MySQL Database ]] local env = assert(luasql.mysql()) local con = assert(env:connect ( dbConf.database ,dbConf.username ,dbConf.passwort ,dbConf.hostname ,dbConf.port )) function checkAuthMySQL(user,pass) local res = con:execute(string.format([[ SELECT * FROM `pwtab` WHERE `name` = '%s' AND `passwort` = '%s' ]], user, pass) ) -- Die Tabelle wir in ein Array gespeichert local row = res:fetch ({}, "a") -- print(type(row)) -- close everything -- res:close() -- already closed because all the result set was consumed con:close() -- env:close() if (not row) then return false else lighty.req_env['REMOTE_USER'] = user return true end end -- MAIN --[[ Check for Authorization Header and force Basic Auth if not set. ]] if (not lighty.request.Authorization) then return doAuth() end --[[ Header found: check string for "Basic" and base64 encoded username & password - upb = User Password Base64 encoded ]] _, _, upb = string.find(lighty.request.Authorization, "^Basic%s+(.+)$") up = mime.unb64(upb) -- Base64 Decode _, _, username, passwort = string.find(up, "^(.+):(.+)$") -- split by ":" to get username and password supplied -- ============================================================================= -- In der DB steht das Passwort nicht im klartext drin, sondern verschlüsselt -- deshalb muss auch der Passwort-Hash und nicht das Passwort verglichen werden. -- -- hier wird aus dem Passwort der Passwort-Hash generiert -- local kommando = ("/usr/bin/php /etc/lighttpd/sha512crypt.php " .. passwort) ausgabe = assert (io.popen (kommando)) pwhash = ausgabe:read ("*l") -- read one line -- ============================================================================= if (not checkAuthMySQL(username, pwhash)) then return doAuth() end end -- return nothing to proceed normal operation return
Leider gibt es nur für eine SHA256-Verschlüsselung eine native LUA-Umsetzung. Für SHA512 müssen wir uns eines externen Programmes (in diesem Fall ein PHP-Skript) bedienen.
<?php $salt = 'tuqu7Cua_ox1jieW'; echo hash('sha512', $salt . $argv[1]); ?>