Module:SMILES2IUPAC
Appearance
| This module is rated as pre-alpha. It is incomplete and may or may not be in active development. Do not use it in article namespace pages. A module remains in pre-alpha until its developer, or another editor who adopts it if it is abandoned for some time, considers the basic structure complete. |
| This module depends on the following other modules: |
Usage
[edit]{{#invoke:SMILES2IUPAC|main}}
local Parser = require('Module:SMILES2IUPAC/Parser')
local Alkanes = require('Module:SMILES2IUPAC/Alkanes')
local Alkenes = require('Module:SMILES2IUPAC/Alkenes')
local Dienes = require('Module:SMILES2IUPAC/Dienes')
local Alkynes = require('Module:SMILES2IUPAC/Alkynes')
local Enynes = require('Module:SMILES2IUPAC/Enynes')
local Functional = require('Module:SMILES2IUPAC/Functional')
local p = {}
local namingSubmodules = {
{ name = 'Functional', tryName = Functional.name },
{ name = 'Enynes', tryName = Enynes.name },
{ name = 'Dienes', tryName = Dienes.name },
{ name = 'Alkenes', tryName = Alkenes.name },
{ name = 'Alkynes', tryName = Alkynes.name },
{ name = 'Alkanes', tryName = Alkanes.name },
}
--- Converts a SMILES string into an IUPAC name.
-- @param smiles string
-- @return name string on success, or nil, errorMessage on failure.
function p.nameFromSmiles(smiles)
local graph, parseErr = Parser.parse(smiles)
if not graph then
return nil, 'could not parse SMILES: ' .. parseErr
end
local lastErr
for _, submodule in ipairs(namingSubmodules) do
local name, err = submodule.tryName(graph)
if name then
return name
end
lastErr = submodule.name .. ': ' .. tostring(err)
end
return nil, 'no naming rule could handle this molecule yet (' .. tostring(lastErr) .. ')'
end
--- {{#invoke:SMILES2IUPAC|main|<smiles>}} entry point.
function p.main(frame)
local args = frame.args
if args.smiles == nil and args[1] == nil and frame:getParent() then
args = frame:getParent().args
end
local smiles = args.smiles or args[1]
if not smiles or smiles == '' then
return 'Error: no SMILES string given'
end
local ok, nameOrErr, err = pcall(p.nameFromSmiles, smiles)
if not ok then
return 'Error: internal error while naming SMILES (' .. tostring(nameOrErr) .. ')'
end
if not nameOrErr then
return 'Error: ' .. tostring(err)
end
return nameOrErr
end
function p.testParser(frame)
local smiles = frame.args[1] or frame.args.smiles
local graph, err = Parser.parse(smiles)
if not graph then
return 'ERROR: ' .. err
end
local out = {}
table.insert(out, 'Atoms:')
for i, atom in ipairs(graph.atoms) do
table.insert(out, i .. ': ' .. atom.element)
end
table.insert(out, 'Bonds:')
for _, bond in ipairs(graph.bonds) do
table.insert(
out,
bond.a .. ' -- ' .. bond.b .. ' (order=' .. bond.order .. ')'
)
end
return table.concat(out, '\n')
end
function p.debugName(frame)
local smiles =
frame.args[1]
or frame.args.smiles
if not smiles or smiles == '' then
return 'Error: no SMILES supplied'
end
local graph, parseErr =
Parser.parse(smiles)
if not graph then
return 'Parser: ' .. tostring(parseErr)
end
local out = {}
for _, submodule in ipairs(namingSubmodules) do
local ok, name, err =
pcall(
submodule.tryName,
graph
)
if not ok then
table.insert(
out,
submodule.name
.. ': CRASH: '
.. tostring(name)
)
elseif name then
table.insert(
out,
submodule.name
.. ': PASS -> '
.. tostring(name)
)
else
table.insert(
out,
submodule.name
.. ': FAIL -> '
.. tostring(err)
)
end
end
return table.concat(out, '\n')
end
function p.debugGraph(frame)
local smiles =
frame.args[1]
or frame.args.smiles
if not smiles or smiles == '' then
return 'Error: no SMILES supplied'
end
local graph, err =
Parser.parse(smiles)
if not graph then
return 'Parser ERROR: ' .. tostring(err)
end
local out = {}
table.insert(
out,
'SMILES: ' .. smiles
)
table.insert(
out,
'Atoms:'
)
for i, atom in ipairs(graph.atoms) do
table.insert(
out,
string.format(
'%d: %s',
i,
atom.element
)
)
end
table.insert(
out,
'Bonds:'
)
for i, bond in ipairs(graph.bonds) do
table.insert(
out,
string.format(
'%d: %d -- %d (order=%d)',
i,
bond.a,
bond.b,
bond.order
)
)
end
return table.concat(
out,
'\n'
)
end
function p.debugAlkene(frame)
local smiles =
frame.args[1]
or frame.args.smiles
if not smiles or smiles == '' then
return 'Error: no SMILES'
end
local graph, err =
Parser.parse(smiles)
if not graph then
return 'Parser: ' .. tostring(err)
end
local ok, result =
pcall(
Alkenes.debugChains,
graph
)
if not ok then
return 'Alkenes ERROR: ' .. tostring(result)
end
return result
end
return p