-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathfta.lua
149 lines (120 loc) · 3.17 KB
/
fta.lua
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
-- lua/fta-score/init.lua
local M = {}
-- Cache to store FTA scores
M.stats = {}
-- Debounce timer
local timer = nil
-- Supported file types
local supported_filetypes = {
javascript = true,
typescript = true,
javascriptreact = true,
typescriptreact = true,
}
-- Function to run fta-cli and get the score
-- Function to run fta-cli and get the score
local function get_fta_score(file_path)
-- Don't process empty or invalid file paths
if not file_path or file_path == "" then
return nil
end
-- Run bunx fta-cli and capture output
local cmd = string.format('bunx fta-cli --json "%s" 2>/dev/null', file_path)
local handle = io.popen(cmd)
if not handle then
return nil
end
-- Use pcall to safely read from handle
local success, output = pcall(function()
local result = handle:read("*a")
handle:close()
return result
end)
-- If reading failed, ensure handle is closed and return nil
if not success then
pcall(handle.close, handle)
return nil
end
-- Parse JSON output with error handling
local parse_success, parsed = pcall(vim.json.decode, output)
if not parse_success or not parsed then
return nil
end
return parsed[1]
end
-- Function to get current buffer file path
local function get_current_file()
local file_path = vim.fn.expand("%:p")
-- Check if it's a real file
if vim.fn.filereadable(file_path) == 0 then
return nil
end
return file_path
end
-- Function to update FTA score for current buffer
function M.update_score()
local file_path = get_current_file()
local file_type = vim.bo.filetype
-- Only process supported file types and valid files
if not file_path or not supported_filetypes[file_type] then
return
end
-- Cancel existing timer if any
if timer then
timer:stop()
timer:close()
end
-- Create new timer with 10ms delay
timer = vim.loop.new_timer()
timer:start(
10,
0,
vim.schedule_wrap(function()
-- Get and cache the score
M.stats[file_path] = get_fta_score(file_path)
-- Force lualine update
vim.cmd("redrawstatus")
end)
)
end
-- Lualine component
function M.get_lualine_component()
return function()
local file_type = vim.bo.filetype
if not supported_filetypes[file_type] then
return "FTA: N/A"
end
local file_path = get_current_file()
if not file_path then
return "FTA: No File"
end
local score = M.stats[file_path]
if score then
return string.format("FTA: %.2f", score.fta_score)
elseif M.stats[file_path] == nil then
return "FTA: calculating..."
else
return "FTA: N/A"
end
end
end
-- Setup function
function M.setup()
-- Create autocmd group
local group = vim.api.nvim_create_augroup("FTAScore", { clear = true })
-- Add autocommands for JavaScript/TypeScript files
vim.api.nvim_create_autocmd({ "BufRead", "BufNewFile", "BufWritePost", "InsertLeave" }, {
pattern = { "*.js", "*.ts", "*.jsx", "*.tsx" },
callback = M.update_score,
group = group,
})
vim.api.nvim_create_user_command("FtaOpen", function()
local file_path = get_current_file()
if not file_path then
return "FTA: No File"
end
local score = M.stats[file_path]
require("utils.float_with_json").create_float_with_json(score)
end, { desc = "Show FTA results for the current file" })
end
return M