Browse Source

add missing files

master
nixo 2 years ago
parent
commit
36b9bae647
  1. 180
      src/dart.jl
  2. 42
      src/pot.jl
  3. 6
      src/types.jl

180
src/dart.jl

@ -0,0 +1,180 @@
function translation_file(translations; interpolation = false)
interpolate = "String fill(List<Object> params) => localizeFill(this, params);"
"""import 'package:i18n_extension/i18n_extension.dart';
extension Localization on String {
static var _t = Translations.byLocale("en_us") +
{
$(translations)
};
$(interpolation ? interpolate : "")
String get i18n => localize(this, _t);
}
"""
end
placeholder(n; place = "STRING") = string(place, "#", string(n, pad=20))
function extract(regex, content)
placeholders = Dict()
for (idx, interp) in enumerate(eachmatch(regex, content))
holder = placeholder(idx, place = "INTERPOLATION")
placeholders[holder] = interp.match
end
placeholders
end
function replace_extracted(content, placeholders)
inv = Dict(map((p) -> p[2] => p[1], collect(placeholders)))
# for placeholder in keys(placeholder)
for key in keys(inv)
content = replace(content, key => inv[key])
end
content
end
function find_all_strings(basepath, filepath)
content = read(joinpath(basepath, filepath), String)
# String interpolation ${} can contain anything (including unescaped strings)
# So it's better to extract it before doing anything
# Replace them with identifiers
placeholders = extract(r"(\$\{.*?\}|\$[A-Za-z][A-Za-z0-9]*)", content)
content = replace_extracted(content, placeholders)
# interpolations = replace(content, r"${.*}" => )
matches =
eachmatch(r"""(?P<quote>'''|'|")(?P<string>.+?)(?<!\\)\k<quote>(?P<i18n>\.i18n)?"""s, content)
# long_lines = [
# placeholder(i, place = "LONGDESCRIPTION") => a for (i, a) in
# filter(m -> occursin("\n", m.match), collect(matches)) |> enumerate
# ] |> Dict
# Now we need to find the lines of the matches.
(placeholders = placeholders,
matches = collect(matches),
content = content)
end
# function find_all_strings(basepath, filepath; i18n = true)
# content = read(joinpath(basepath, filepath), String)
# # Remove comments
# content = replace(content, r"""///?.*"""m => "")
# content = replace(content, r"""/\*.*?\*/"""s => "")
# # Remove imports/export
# content = replace(content, r"""(import|export|part) .*"""m => "")
# # Mark new lines to extract string positions
# lines = findall(x -> x == '\n', collect(content))
# # Find all types of strings
# # ? EXCLUDE PRINT?
# strings = eachmatch(r"""(['"])(.*?)\1(\.i18n)?""", content)
# out = []
# for string in strings
# (i18n && isnothing(string[3])) && continue
# # TODO: Interactively modify the source code to:
# # 1. Add the .i18n
# # 2. Include the file
# # Get the line of the match
# line = findfirst(line -> line >= string.offset, lines)
# push!(out, (file = filepath, line = line, strid = string[2]))
# end
# out
# end
dartfiles(files) = filter(f -> endswith(f, ".dart"), files)
function find_dart_files(path)
out = []
for (root, dirs, files) in walkdir(path)
for file in dartfiles(files)
push!(out, joinpath(root, file))
end
end
out
end
function find_all_strings(path)
no_i18n(files) = filter(f -> !endswith(f, "i18n.dart"), files)
excluded(files) = filter(f -> !(f in exclude), files)
path = realpath(path)
files = find_dart_files(path) |> no_i18n
find_all_strings.(Ref(path), files)
end
read_dart_project(path; exclude = []) = find_all_strings(path, exclude = exclude, i18n = true)
function i18n_project(path)
exc = ".i18n-excluded"
ign = ".i18n-ignored"
splitter = "\0¤\0"
ignored = isfile(ign) ? map(l -> split(l, splitter), readlines(ign)) : []
new_excludes = []
edits = []
adds = []
cd(path) do
exclude = isfile(exc) ? readlines(exc) : []
strings = vcat(find_all_strings(path; exclude = exclude, i18n = false)...)
files = map(s -> s.file, strings) |> unique
@info "You have a total of $(length(strings)) strings in $(length(files)) files"
@warn "!!!Remember to git commit before running this!!!"
for file in files
content = readlines(file)
@info "Inspecting file $(file)?"
for str in filter(s -> s.file == file, strings)
if !isnothing(findfirst(i -> i[1] == str.file &&
i[2] == string(str.line) &&
i[3] == str.strid, ignored))
continue
end
println("Line $(str.line): >$(str.strid)< ")
println(content[str.line])
println("[e]xclude, [a]dd, [c]hange, [i]gnore")
resp = ' '
while !(resp in ["e", "a", "c", "i"])
resp = readline(stdin)
end
if resp == "e"
push!(new_excludes, file)
break
elseif resp == "a"
push!(adds, str)
continue
elseif resp == "c"
push!(edits, str => readline(stdin))
elseif resp == "i"
open(ign, "a+") do f
println(f, join([str.file, str.line, str.strid], splitter))
end
continue
else
@error "Unknown problem"
end
end
end
end
## Process changes
@warn "Applying changes in 3s... last chance to interrupt (Ctrl-C)"
sleep(3)
open(exc, "a+") do f
write(f, join(new_excludes, "\n"))
end
edits, adds
end
struct Translation
lang::String
msgstr::String
end
struct Translatable
msgid::String
translations::Array{Translation}
file::Union{String,Nothing}
line::Union{UInt,Nothing}
end
function dart_to_pot(path)
files = find_all_strings(path)
for file in files
i18n_s = filter(!isnothing, map(m -> m["i18n"], file.matches))
length(i18n_s) == 0 && continue
@show i18n_s
end
end

42
src/pot.jl

@ -0,0 +1,42 @@
# Pot import/export functions
is_comment(line; char = r"#") = startswith(line, char)
function readpot(path, lang, name = "base")
lines = readlines(joinpath(path, lang, "LC_MESSAGES", string(name, ".pot")))
filter!(x -> !is_comment(x, char = r"#(?!:)"), lines)
filter!(!isempty, lines)
lines = lines[3:end]
@assert length(lines) % 3 == 0
output = []
for l in 1:3:length(lines)
ref = split(lines[l], "#: ")
msgid = split(lines[l+1], "msgid ")
msgstr = split(lines[l+2], "msgstr ")
@assert length(ref) == 2
@assert length(msgid) == 2
@assert length(msgstr) == 2
id = split(msgid[2], '"')
str = split(msgstr[2], '"')
if length(id) != 3 && l != 1
@warn "Problems with $msgstr $msgid"
continue
end
if isempty(str[2])
continue
end
push!(output, (lang, id[2], str[2], split(ref[2], ":")[1]))
end
output
end
function pot_to_jl(lang, id)
"""@translate "$lang" "$(id[2])" "$(str[2])" """
end
function pot_to_jl(srcpath, destpath, filename, basename)
langs = readdir(srcpath)
content = join([join(readpot(srcpath, lang, basename), "\n")
for lang in langs], "\n\n")
write(joinpath(destpath, string(filename, ".jl")), content)
end

6
src/types.jl

@ -0,0 +1,6 @@
struct Translatable
string::AbastractString
file::String
line::Int
end
Loading…
Cancel
Save