support running tests multiple times

[?]
Jan 21, 2023, 4:07 AM
JNJ4R56X3HVU4IGKZZ2IV73PALEXSYOIOAIVXZTV43BG7PEY6AOQC

Dependencies

  • [2] FCFJVYKY redundant check
  • [3] S4IAYCIR delete all tests once they've executed
  • [4] UVSNG336 reclaim a couple more functions after tests
  • [5] JCXL74WV bring back everything from commit a68647ae22
  • [6] 2CK5QI7W make love event names consistent
  • [7] PESSMQBJ no, make sure to compute line width after screen dimensions
  • [8] JFFUF5AL override mouse state lookups in tests
  • [9] 36Z442IV back to commit 8123959e52f without code editing
  • [10] AD34IX2Z couple more tests
  • [11] PX7DDEMO autosave slightly less aggressively
  • [12] ZLJGZYQG select text with shift + mouseclick
  • [13] 2CTN2IEF Merge lines.love
  • [14] AVTNUQYR basic test-enabled framework
  • [15] IMEJA43L snapshot
  • [16] KKMFQDR4 editing source code from within the app
  • [17] JF5L2BBS test harness now supports copy/paste
  • [18] 3QNOKBFM beginnings of a test harness
  • [19] HKV72RZV bugfix: save modified files in save directory
  • [20] JMUD7T3O get rid of ugly side-effects in tests
  • [21] JOPVPUSA editing source code from within the app
  • [22] 7CLGG7J2 test: autosave after any shape

Change contents

  • edit in app.lua at line 15
    [5.4091]
    [7.84]
    -- have LÖVE delegate all handlers to App if they exist
    for name in pairs(love.handlers) do
    if App[name] then
    love.handlers[name] = App[name]
    end
    end
    -- Stash current state of App for tests
    App_for_tests = {}
    for k,v in pairs(App) do
    App_for_tests[k] = v
    end
    -- there's one nested table
    App_for_tests.screen = {}
    for k,v in pairs(App.screen) do
    App_for_tests.screen[k] = v
    end
    -- Mutate App for the real app
    -- disable test methods
    App.screen.init = nil
    App.filesystem = nil
    App.time = nil
    App.run_after_textinput = nil
    App.run_after_keychord = nil
    App.keypress = nil
    App.keyrelease = nil
    App.run_after_mouse_click = nil
    App.run_after_mouse_press = nil
    App.run_after_mouse_release = nil
    App.fake_keys_pressed = nil
    App.fake_key_press = nil
    App.fake_key_release = nil
    App.fake_mouse_state = nil
    App.fake_mouse_press = nil
    App.fake_mouse_release = nil
    -- dispatch some methods to real hardware
    App.screen.resize = love.window.setMode
    App.screen.size = love.window.getMode
    App.screen.move = love.window.setPosition
    App.screen.position = love.window.getPosition
    App.screen.print = love.graphics.print
    App.newText = love.graphics.newText
    App.screen.draw = love.graphics.draw
    App.width = function(text) return text:getWidth() end
    App.open_for_reading = function(filename) return io.open(filename, 'r') end
    App.open_for_writing = function(filename) return io.open(filename, 'w') end
    App.getTime = love.timer.getTime
    App.getClipboardText = love.system.getClipboardText
    App.setClipboardText = love.system.setClipboardText
    App.modifier_down = love.keyboard.isDown
    App.mouse_move = love.mouse.setPosition
    App.mouse_down = love.mouse.isDown
    App.mouse_x = love.mouse.getX
    App.mouse_y = love.mouse.getY
  • edit in app.lua at line 72
    [7.8462]
    [7.8462]
    -- example handler
    if #Test_errors > 0 then
    error('\n\n'..table.concat(Test_errors, '\n'))
    end
  • edit in app.lua at line 77
    [7.8463][7.258:276](),[7.209277][7.258:276](),[7.209821][7.258:276](),[7.2321][7.258:276](),[7.276][7.8464:8486]()
    --? print('==')
    App.disable_tests()
  • edit in app.lua at line 429
    [7.8001]
    [7.8001]
    local saved_app = App
    App = App_for_tests
    Test_errors = {}
  • replacement in app.lua at line 434
    [2.47][2.47:62]()
    _G[name]()
    [2.47]
    [7.7548]
    local status, err = xpcall(_G[name], handle_error_in_test)
  • replacement in app.lua at line 437
    [7.7564][3.17:113]()
    -- clean up all test methods
    for _,name in ipairs(sorted_names) do
    _G[name] = nil
    end
    [7.7564]
    [7.7564]
    App = saved_app
  • replacement in app.lua at line 440
    [7.7569][7.7569:7887](),[7.7887][4.19:67](),[4.67][7.7887:7911](),[7.7887][7.7887:7911](),[7.7911][7.2657:2680](),[7.2680][7.1619:1636](),[7.1636][7.7911:7943](),[7.2680][7.7911:7943](),[7.7911][7.7911:7943](),[7.7943][7.2681:2712](),[7.2712][7.2192:2236](),[7.2236][7.1637:1741](),[7.1741][6.7869:7899](),[6.7899][7.5388:5533](),[7.5388][7.5388:5533](),[7.2262][7.7943:7988](),[7.2712][7.7943:7988](),[7.5533][7.7943:7988](),[7.7943][7.7943:7988](),[7.7988][5.5112:5286](),[7.1365][7.7988:8162](),[5.5286][7.7988:8162](),[7.7988][7.7988:8162](),[7.8162][7.8570:8726](),[7.913][7.1742:1777](),[7.8726][7.1742:1777](),[7.2791][7.1742:1777](),[7.1777][7.2953:3061](),[7.2791][7.2953:3061](),[7.3061][7.2263:2306](),[7.2306][7.5534:5677]()
    -- call this once all tests are run
    -- can't run any tests after this
    function App.disable_tests()
    -- have LÖVE delegate all handlers to App if they exist
    for name in pairs(love.handlers) do
    if App[name] then
    love.handlers[name] = App[name]
    end
    end
    -- test methods are disallowed outside tests
    App.run_tests = nil
    App.disable_tests = nil
    App.screen.init = nil
    App.filesystem = nil
    App.time = nil
    App.run_after_textinput = nil
    App.run_after_keychord = nil
    App.keypress = nil
    App.keyrelease = nil
    App.run_after_mouse_click = nil
    App.run_after_mouse_press = nil
    App.run_after_mouse_release = nil
    App.fake_keys_pressed = nil
    App.fake_key_press = nil
    App.fake_key_release = nil
    App.fake_mouse_state = nil
    App.fake_mouse_press = nil
    App.fake_mouse_release = nil
    -- other methods dispatch to real hardware
    App.screen.resize = love.window.setMode
    App.screen.size = love.window.getMode
    App.screen.move = love.window.setPosition
    App.screen.position = love.window.getPosition
    App.screen.print = love.graphics.print
    App.newText = love.graphics.newText
    App.screen.draw = love.graphics.draw
    App.width = function(text) return text:getWidth() end
    App.open_for_reading = function(filename) return io.open(filename, 'r') end
    App.open_for_writing = function(filename) return io.open(filename, 'w') end
    App.getTime = love.timer.getTime
    App.getClipboardText = love.system.getClipboardText
    App.setClipboardText = love.system.setClipboardText
    App.modifier_down = love.keyboard.isDown
    App.mouse_move = love.mouse.setPosition
    App.mouse_down = love.mouse.isDown
    App.mouse_x = love.mouse.getX
    App.mouse_y = love.mouse.getY
    [7.7569]
    [7.8162]
    function handle_error_in_test(err)
    local full_error = debug.traceback('Error: '..err, --[[stack frame]]3):gsub('\n[^\n]+$', '')
    table.insert(Test_errors, full_error..'\n')