462 lines
23 KiB
Python
462 lines
23 KiB
Python
import uuid
|
|
from django.core.exceptions import ValidationError
|
|
from arches.app.functions.base import BaseFunction
|
|
from arches.app.models.system_settings import settings
|
|
from arches.app.models import models
|
|
from arches.app.models.tile import Tile
|
|
from django.db import connection, transaction
|
|
import re
|
|
import json
|
|
import logging
|
|
|
|
details = {
|
|
"name": "Datos iniciales",
|
|
"type": "node",
|
|
"description": "Establece los datos iniciales de las instancias de recursos",
|
|
"defaultconfig": {
|
|
"lugar": {"ndeId": "", "ndegrpId": ""},
|
|
"lugar_amplio": {"ndeId": "", "ndegrpId": ""},
|
|
"alcance": {"ndeId": "", "ndegrpId": ""},
|
|
"eta": {"ndeId": "", "ndegrpId": ""},
|
|
"codigo": {"ndeId": "", "ndegrpId": ""},
|
|
"nombre": {"ndeId": "", "ndegrpId": ""},
|
|
"meta_ubicacion": {"ndeId": "", "ndegrpId": ""},
|
|
"meta_identificacion": {"ndeId": "", "ndegrpId": ""},
|
|
"meta_marco_legal": {"ndeId": "", "ndegrpId": ""},
|
|
"meta_caracteristicas": {"ndeId": "", "ndegrpId": ""},
|
|
"valor_ndeId": "",
|
|
"valor_ponderado_ndeId": "",
|
|
"valor_ajuste_ndeId": "",
|
|
"valor_rango_ndeId": "",
|
|
"triggering_nodegroups": [],
|
|
},
|
|
"classname": "DatosInicio",
|
|
"component": "views/components/functions/datos-iniciales",
|
|
"functionid": "6ec500db-51cc-4cc8-a796-ee46a56f6998",
|
|
}
|
|
|
|
class DatosInicio(BaseFunction):
|
|
|
|
def get(self):
|
|
raise NotImplementedError
|
|
|
|
def componer_codigo(self, tile, request, is_function_save_method=True):
|
|
"""
|
|
Función que construye el código de identificación de ficha, en base a
|
|
la ubicación, ámbito y una secuencia numérica
|
|
|
|
Args:
|
|
self: Objeto código.
|
|
tile: Tile al que se adjuntará/modificará el código.
|
|
request: Solicitud WSGI utilizada para verificar que la llamada sea resultado de una acción del usuario.
|
|
Nota: La función devuelve el valor si está vacío.
|
|
is_function_save_method: Un valor booleano que indica si la función que lo llama es la función de guardado.
|
|
|
|
jbti - 20.9.25
|
|
"""
|
|
#Comprueba que sea un llamado válido
|
|
if request is None and is_function_save_method == True:
|
|
return
|
|
|
|
def actualizar_descriptors(str_ficha_id):
|
|
try:
|
|
qry = f"""
|
|
UPDATE resource_instances
|
|
SET descriptors = jsonb_set(
|
|
descriptors,
|
|
'{{es,map_popup}}', '"Indefinido"')
|
|
WHERE resourceinstanceid = '{str_ficha_id}'
|
|
AND descriptors->'es'->>'map_popup' LIKE '<%>'
|
|
RETURNING descriptors->'es'->>'map_popup';
|
|
"""
|
|
with connection.cursor() as cursor:
|
|
cursor.execute(qry)
|
|
nvo_descriptor = cursor.fetchone()
|
|
if nvo_descriptor is not None:
|
|
return nvo_descriptor
|
|
else:
|
|
return ('Sin actualizar',)
|
|
|
|
except Exception as e:
|
|
self.logger.error(e,"\t*** Falla al actualizar descriptor")
|
|
|
|
def extraer_depto(str_val_depto): # retorna el departamento como str_concept_value
|
|
try:
|
|
div_admin = '4f6caa05-23e3-42a4-8322-98b914fb3ebf' # (División administrativa)
|
|
region = '2eb6660c-1754-42cf-959d-0edaf7779dae' # Region de Bolivia
|
|
qry = f"""
|
|
SELECT val.valueid::text, val.value
|
|
FROM values val
|
|
JOIN values vval
|
|
ON val.conceptid = vval.conceptid
|
|
JOIN relations rel
|
|
ON val.conceptid = rel.conceptidto
|
|
WHERE val.valuetype = 'prefLabel'
|
|
AND vval.valuetype = 'hiddenLabel'
|
|
AND (
|
|
rel.conceptidfrom = '{div_admin}'
|
|
OR rel.conceptidfrom = '{region}')
|
|
AND vval.value = '{str_val_depto}';
|
|
"""
|
|
with connection.cursor() as cursor:
|
|
cursor.execute(qry)
|
|
departamento = cursor.fetchone()
|
|
if departamento is not None:
|
|
return departamento
|
|
else:
|
|
return ()
|
|
except Exception as e:
|
|
self.logger.error(e,"\t*** Falla al extraer departamento")
|
|
|
|
def establecer_grupos(string_id_recurso, int_id_grp_eta, sufijo_eta_model, esRecurso = True):
|
|
int_id_todas_las_etas = 10000
|
|
int_id_eta_model = int_id_grp_eta + sufijo_eta_model
|
|
try:
|
|
qry = f"""
|
|
INSERT INTO guardian_groupobjectpermission (object_pk, content_type_id, group_id, permission_id)
|
|
VALUES
|
|
('{string_id_recurso}',33,2,130),
|
|
('{string_id_recurso}',33,2,131),
|
|
('{string_id_recurso}',33,{int_id_todas_las_etas},132),
|
|
('{string_id_recurso}',33,{int_id_grp_eta},132),
|
|
('{string_id_recurso}',33,{int_id_eta_model},132)
|
|
ON CONFLICT (group_id, permission_id, object_pk) DO NOTHING;
|
|
"""
|
|
with connection.cursor() as cursor:
|
|
cursor.execute(qry)
|
|
|
|
except Exception as e:
|
|
self.logger.error(e,"\t*** Falla al establecer grupos")
|
|
|
|
def es_ambito(string_id_concepto_value):
|
|
qry = f"""
|
|
SELECT CASE WHEN EXISTS (
|
|
SELECT *
|
|
FROM relations r RIGHT JOIN values v ON r.conceptidfrom = v.conceptid
|
|
WHERE r.relationtype = 'narrower' AND v.valueid = '{string_id_concepto_value}'
|
|
)
|
|
THEN CAST(1 AS BIT)
|
|
ELSE CAST(0 AS BIT) END;
|
|
"""
|
|
with connection.cursor() as cursor:
|
|
cursor.execute(qry)
|
|
esAmbito = cursor.fetchone()[0]
|
|
return esAmbito
|
|
|
|
def extraer_concepto_valor(string_id_concepto_value, str_tipo_valor): # return string numeric code
|
|
qry = f"""
|
|
SELECT val.value FROM values val INNER JOIN values v ON v.conceptid = val.conceptid
|
|
WHERE val.valuetype='{str_tipo_valor}' AND v.valueid='{string_id_concepto_value}'
|
|
"""
|
|
with connection.cursor() as cursor:
|
|
cursor.execute(qry)
|
|
valorConcepto = cursor.fetchone()
|
|
if valorConcepto is not None:
|
|
return valorConcepto[0]
|
|
else:
|
|
return '00'
|
|
|
|
def extraer_datos_recurso(string_id_recurso): # Return ['graph_id', principaluser_id]
|
|
if string_id_recurso is not None:
|
|
qry = f"""
|
|
SELECT graphid::text, principaluser_id FROM resource_instances
|
|
WHERE resourceinstanceid ='{string_id_recurso}'
|
|
"""
|
|
cursor = connection.cursor()
|
|
cursor.execute(qry)
|
|
datos_recurso = list(cursor.fetchone())
|
|
cursor.close()
|
|
else:
|
|
datos_recurso = []
|
|
return datos_recurso
|
|
|
|
def extraer_etaId(usuario_id): # Return 'recurso_eta_id'
|
|
eta_grp_ndeId = '263826f2-f4d9-11ef-822e-0242ac120006'
|
|
qry = f"""
|
|
SELECT t.resourceinstanceid AS etaid, ug.eta_grpid AS etagrp FROM tiles t
|
|
JOIN (
|
|
SELECT user_id, ((MAX(group_id) / 100) * 100) AS eta_grpid
|
|
FROM auth_user_groups WHERE group_id > 9999 GROUP BY user_id) ug
|
|
ON t.tiledata['{eta_grp_ndeId}']::int = ug.eta_grpid
|
|
WHERE ug.user_id = {usuario_id} AND t.nodegroupid = '{eta_grp_ndeId}';
|
|
"""
|
|
with connection.cursor() as cursor:
|
|
cursor.execute(qry)
|
|
etaNdeId = cursor.fetchone()
|
|
if etaNdeId is not None :
|
|
return etaNdeId
|
|
else:
|
|
return ['deb0ae78-56f1-4bcf-abb2-d02ffcdd33c1', 10100] # Actor Min.Culturas
|
|
|
|
def insertar_actor(rsi_id, eta_tileid, eta_actorid, eta_ndeid, GraphId, eta_ndegrpid):
|
|
ontProp = 'ac41d9be-79db-4256-b368-2f4559cfbe55'
|
|
actorGraphId = '72420da0-db59-4048-aea2-03b0bc5cdcdf'
|
|
|
|
try:
|
|
qry = f"""
|
|
INSERT INTO resource_x_resource (
|
|
resourcexid, relationshiptype,
|
|
resourceinstanceidfrom,
|
|
resourceinstanceidto,
|
|
modified, created, inverserelationshiptype,
|
|
tileid,
|
|
nodeid,
|
|
resourceinstancefrom_graphid,
|
|
resourceinstanceto_graphid
|
|
)
|
|
VALUES (
|
|
gen_random_uuid(), '{ontProp}',
|
|
'{rsi_id}',
|
|
'{eta_actorid}',
|
|
now(), now(), '{ontProp}',
|
|
'{eta_tileid}',
|
|
'{eta_ndeid}',
|
|
'{GraphId}',
|
|
'{actorGraphId}'
|
|
) returning resourcexid
|
|
"""
|
|
with connection.cursor() as cursor:
|
|
cursor.execute(qry)
|
|
nvo_resxid = cursor.fetchone()[0]
|
|
qry2 = f"""
|
|
UPDATE tiles SET tiledata = jsonb_set(
|
|
tiledata,
|
|
'{{{eta_ndeid}}}', '[{{
|
|
"resourceId": "{eta_actorid}",
|
|
"ontologyProperty": "{ontProp}",
|
|
"resourceXresourceId": "{nvo_resxid}",
|
|
"inverseOntologyProperty": "{ontProp}"
|
|
}}]'
|
|
)
|
|
WHERE nodegroupid = '{eta_ndegrpid}'
|
|
AND resourceinstanceid = '{rsi_id}'
|
|
returning tiledata
|
|
"""
|
|
cursor.execute(qry2)
|
|
cursor.close()
|
|
|
|
except Exception as e:
|
|
self.logger.error(e,"\t*** Falla al insertar actor")
|
|
|
|
def actualizar_codigo(MetaCodigo):
|
|
#calculo de la secuencia
|
|
nvo_codigo = [MetaCodigo['tipoM'],MetaCodigo['codU'], MetaCodigo['codAm'], MetaCodigo['codsA'], MetaCodigo['num']]
|
|
#languages = models.Language.objects.all()
|
|
#default_language = languages.get(code=settings.LANGUAGE_CODE)
|
|
#return {default_language.code: {"value": '-'.join(nvo_codigo), "direction": default_language.default_direction}}
|
|
return '-'.join(nvo_codigo)
|
|
|
|
def extraer_num_siguiente(strCod_ndeId, strCod_ndegrpId, MetaCodigo): # Return int
|
|
str_cod_num = '-'.join([MetaCodigo['tipoM'],MetaCodigo['codU'], MetaCodigo['codAm'], MetaCodigo['codsA']])
|
|
qry = f"""
|
|
SELECT MAX(regexp_match(tiledata->>'{strCod_ndeId}','-(\d+)$')) AS max_cod_num
|
|
FROM tiles WHERE nodegroupid = '{strCod_ndegrpId}'
|
|
AND tiledata->>'{strCod_ndeId}' LIKE '{str_cod_num}%';
|
|
"""
|
|
with connection.cursor() as cursor:
|
|
cursor.execute(qry)
|
|
ultimo_num = cursor.fetchone()
|
|
if ultimo_num is not None and ultimo_num[0] is not None:
|
|
print(f"Siguiente número del código: {ultimo_num}")
|
|
return str(int(ultimo_num[0][0]) + 1)
|
|
else:
|
|
return str(1)
|
|
|
|
def extraer_metavalor(metavalor_ngId, metavalor_nId, resource_id, metavalor={}): # Retorna o actualiza metavalor dict
|
|
metaValor_tiles = Tile.objects.filter(nodegroup_id = str(metavalor_ngId), resourceinstance_id = resource_id)
|
|
metavalor_actual = {}
|
|
if len(metaValor_tiles) > 0 :
|
|
metaValor_tile = metaValor_tiles[0]
|
|
if metavalor_nId in metaValor_tile.data and metaValor_tile.data[metavalor_nId] is not None:
|
|
metavalor_actual = eval(metaValor_tile.data[metavalor_nId])
|
|
|
|
elif len(metaValor_tiles) == 0 and len(metavalor) > 0:
|
|
metavalor_actual.update(metavalor)
|
|
metaValor_tile = Tile.get_blank_tile_from_nodegroup_id(metavalor_ngId, resource_id, None)
|
|
metaValor_tile.data[metavalor_nId] = str(metavalor_actual)
|
|
metaValor_tile.save()
|
|
|
|
return metavalor_actual
|
|
|
|
def extraer_codigo(codigo_ngId, codigo_nId, resource_id): # Return str
|
|
cod_num = ""
|
|
codigo_tiles = Tile.objects.filter(nodegroup_id = str(codigo_ngId), resourceinstance_id = resource_id)
|
|
if len(codigo_tiles) > 0 :
|
|
for codi in codigo_tiles :
|
|
# Si el código es del tipo principal
|
|
codigo_tile = codi if 'c07032eb-b50a-4048-b18c-bde5e8e6ad6a' in codi.data.values() else codigo_tiles[0]
|
|
if codigo_nId in codigo_tile.data and codigo_tile.data[codigo_nId] is not None:
|
|
#cod_num = str(codigo_tile.data[codigo_nId]['es']['value'])
|
|
cod_num = str(codigo_tile.data[codigo_nId])
|
|
cod_num = re.sub(r'^(.+)-','',cod_num)
|
|
if cod_num != '' : cod_num = cod_num.rjust(6,'0')
|
|
return cod_num
|
|
|
|
try:
|
|
# procedimiento para definir los metadatos
|
|
|
|
metaCodlugar = {'tipoM': 'PM', 'codU': '000000', 'num': '000000'}
|
|
metaCodIden = {'codAm': '00', 'codsA': '00'}
|
|
metaGrupo = {'grp_eta': 10100, 'sufijo_grp_model': 0}
|
|
datos_recurso = extraer_datos_recurso(tile.resourceinstance_id) # ['graph_id', principaluser_id]
|
|
etaActor_id_grp = extraer_etaId(datos_recurso[1])
|
|
etaActor_id = etaActor_id_grp[0]
|
|
metaGrupo.update({'grp_eta': etaActor_id_grp[1]})
|
|
es_patrimonio = True
|
|
match datos_recurso[0]:
|
|
case '72420da0-db59-4048-aea2-03b0bc5cdcdf' : # Actores
|
|
es_patrimonio = False
|
|
metaGrupo.update({'sufijo_grp_model': 17})
|
|
|
|
case '6afc4e9e-727e-4152-8084-309267752650' : # Medios
|
|
es_patrimonio = False
|
|
metaGrupo.update({'sufijo_grp_model': 16})
|
|
|
|
case "2bf240e6-718e-44f0-8073-4962d84931fe" : # Si el modelo es del tipo actividades
|
|
metaGrupo.update({'sufijo_grp_model': 15})
|
|
|
|
case '76331d8a-4d85-11ee-a708-ffcd06c08a5d': # Si el modelo es del tipo arqueologico
|
|
metaGrupo.update({'sufijo_grp_model': 14})
|
|
|
|
case '9b0e22c7-5c56-4be6-aa89-ae2632ba28e8': # Si el modelo es del tipo inmaterial
|
|
metaCodlugar.update({'tipoM': 'PI'})
|
|
metaGrupo.update({'sufijo_grp_model': 13})
|
|
|
|
case '10b03fec-4d85-11ee-a708-ffcd06c08a5d': # Si el modelo es del tipo bienes muebles
|
|
metaGrupo.update({'sufijo_grp_model': 12})
|
|
|
|
case '8ea3bf67-89ce-474c-b3cb-6dd5ee3d6198': # Si el modelo es del tipo bienes inmuebles
|
|
metaCodlugar.update({'num': 'D00M00L00'})
|
|
metaGrupo.update({'sufijo_grp_model': 11})
|
|
|
|
metaIden_ndegrp = self.config['meta_identificacion']['ndegrpId']
|
|
metaIden_nde = self.config['meta_identificacion']['ndeId']
|
|
lugarAmplio_nde = self.config['lugar_amplio']['ndeId']
|
|
metaIden = {}
|
|
tup_depto = ()
|
|
if es_patrimonio:
|
|
# procedimiento para fijar el el actor administrativo
|
|
eta_ndegrpId = self.config['eta']['ndegrpId']
|
|
eta_ndeId = self.config['eta']['ndeId']
|
|
etaTile = Tile.objects.filter(nodegroup_id=str(eta_ndegrpId), resourceinstance_id=tile.resourceinstance_id)
|
|
if len(etaTile) == 0:
|
|
eta_tile = Tile.get_blank_tile_from_nodegroup_id(eta_ndegrpId, tile.resourceinstance_id, None)
|
|
eta_tile.save()
|
|
insertar_actor(tile.resourceinstance_id, str(eta_tile.tileid), etaActor_id, eta_ndeId, datos_recurso[0], eta_ndegrpId)
|
|
|
|
metaLugar_ndegrp = self.config['meta_ubicacion']['ndegrpId']
|
|
metaLugar_nde = self.config['meta_ubicacion']['ndeId']
|
|
codigo_ndegrp = self.config['codigo']['ndegrpId']
|
|
codigo_nde = self.config['codigo']['ndeId']
|
|
codigo_num = metaCodlugar['num']
|
|
|
|
# Código de lugar a meta lugar
|
|
if str(tile.nodegroup_id) == self.config['lugar']['ndegrpId']:
|
|
lugar_value = tile.data[self.config["lugar"]["ndeId"]]
|
|
if lugar_value is not None :
|
|
lugar_cod_value = extraer_concepto_valor(lugar_value, "hiddenLabel")
|
|
if len(lugar_cod_value) > 2 :
|
|
lugar_cod_value = lugar_cod_value.ljust(5,'0')
|
|
lugar_cod_value = lugar_cod_value.rjust(6,'0')
|
|
else:
|
|
lugar_cod_value = lugar_cod_value.ljust(6,'0')
|
|
metaCodlugar.update(codU = lugar_cod_value)
|
|
# establecer lugar extendido
|
|
tup_depto = extraer_depto(lugar_cod_value[0:2])
|
|
print("\t*** tup_depto: ",tup_depto)
|
|
else:
|
|
tup_depto = extraer_depto('00')
|
|
|
|
if len(tup_depto) > 0 and tup_depto[0] is not None: tile.data[self.config['lugar_amplio']['ndeId']] = [str(tup_depto[0])]
|
|
|
|
# extraer/crear número del código
|
|
num_anterior = extraer_codigo(codigo_ndegrp, codigo_nde, tile.resourceinstance_id)
|
|
if num_anterior != '' : metaCodlugar.update({'num': num_anterior})
|
|
|
|
tile.data[metaLugar_nde] = str(metaCodlugar)
|
|
|
|
# Ámbito a meta identificacion y código si es el caso
|
|
if str(tile.nodegroup_id) == metaIden_ndegrp and codigo_ndegrp == metaIden_ndegrp :
|
|
metalugar = extraer_metavalor(metaLugar_ndegrp, metaLugar_nde, tile.resourceinstance_id)
|
|
if 'tipoM' in metalugar: metaCodlugar.update({'tipoM': metalugar['tipoM']})
|
|
if 'codU' in metalugar: metaCodlugar.update({'codU': metalugar['codU']})
|
|
if 'num' in metalugar: metaCodlugar.update({'num': metalugar['num']})
|
|
alcance_cod_values = tile.data[self.config["alcance"]["ndeId"]]
|
|
if alcance_cod_values is not None:
|
|
match len(alcance_cod_values):
|
|
case 0:
|
|
metaCodIden = {'codAm': '00', 'codsA': '00'}
|
|
case 1:
|
|
metaCodIden = {'codAm': extraer_concepto_valor(alcance_cod_values[0], "hiddenLabel").rjust(2,'0'), 'codsA': '00'}
|
|
if es_ambito(alcance_cod_values[0]) == '1':
|
|
metaCodIden = {'codAm': extraer_concepto_valor(alcance_cod_values[0], "hiddenLabel").rjust(2,'0'), 'codsA': '00'}
|
|
else:
|
|
metaCodIden = {'codAm': '00', 'codsA': extraer_concepto_valor(alcance_cod_values[0], "hiddenLabel").rjust(2,'0')}
|
|
case _ if len(alcance_cod_values) > 1: # Falta completar validación de ámbito y subambito
|
|
if es_ambito(alcance_cod_values[0]) == '1':
|
|
metaCodIden = {'codAm': extraer_concepto_valor(alcance_cod_values[0], "hiddenLabel").rjust(2,'0'), 'codsA':
|
|
extraer_concepto_valor(alcance_cod_values[1], "hiddenLabel").rjust(2,'0')}
|
|
else:
|
|
metaCodIden = {'codAm': extraer_concepto_valor(alcance_cod_values[1], "hiddenLabel").rjust(2,'0'), 'codsA':
|
|
extraer_concepto_valor(alcance_cod_values[0], "hiddenLabel").rjust(2,'0')}
|
|
metacodigo = metaCodlugar | metaCodIden
|
|
metaIden.update(metaCodIden)
|
|
metaIden.update(metaGrupo)
|
|
|
|
# Procesado del número del código
|
|
if codigo_nde in tile.data and tile.data[codigo_nde] is not None :
|
|
codigo_num = str(tile.data[codigo_nde])
|
|
codigo_num = re.sub(r'^(.+)-','',codigo_num)
|
|
|
|
if "?" in re.sub(r'^(.+)-','',codigo_num) or codigo_num == '000000':
|
|
metacodigo.update(num = extraer_num_siguiente(codigo_nde, codigo_ndegrp, metacodigo).rjust(6,'0'))
|
|
else:
|
|
metacodigo.update(num = codigo_num.rjust(6,'0'))
|
|
|
|
tile.data[self.config['codigo']['ndeId']] = actualizar_codigo(metacodigo)
|
|
|
|
# insertar permisos de ficha
|
|
metaiden = extraer_metavalor(metaIden_ndegrp, metaIden_nde, tile.resourceinstance_id)
|
|
if "grp_eta" not in metaiden :
|
|
establecer_grupos(tile.resourceinstance_id, metaGrupo['grp_eta'], metaGrupo['sufijo_grp_model'])
|
|
print("\t*** metacodigo : ", metacodigo)
|
|
metaIden.update(metaGrupo)
|
|
tile.data[metaIden_nde] = str(metaIden)
|
|
|
|
if str(tile.nodegroup_id) == self.config['nombre']['ndegrpId'] and not es_patrimonio:
|
|
print("\t*** insertar permisos de ficha complementaria")
|
|
metaIden = extraer_metavalor(metaIden_ndegrp, metaIden_nde, tile.resourceinstance_id)
|
|
if "grp_eta" not in metaIden :
|
|
establecer_grupos(tile.resourceinstance_id, metaGrupo['grp_eta'], metaGrupo['sufijo_grp_model'])
|
|
metaIden = extraer_metavalor(metaIden_ndegrp, metaIden_nde, tile.resourceinstance_id, metaGrupo)
|
|
|
|
print("\t*** metaIden : ", metaIden,"\n")
|
|
print("\t*** Nvo. map_popup: ",actualizar_descriptors(tile.resourceinstance_id)[0])
|
|
return
|
|
|
|
except Exception as e:
|
|
self.logger.error(e,"\t*** Falla al fijar los datos iniciales")
|
|
return
|
|
|
|
def save(self, tile, request, context=None):
|
|
self.logger = logging.getLogger(__name__)
|
|
print("\n\t*** llamado a la función datos_iniciales.save ***")
|
|
self.componer_codigo(tile=tile, request=request, is_function_save_method=True)
|
|
return
|
|
|
|
# occurrs after Tile.save
|
|
def post_save(self, *args, **kwargs):
|
|
raise NotImplementedError
|
|
|
|
def delete(self, tile, request):
|
|
raise NotImplementedError
|
|
|
|
def on_import(self, tile):
|
|
self.componer_codigo(tile=tile, request=None, is_function_save_method=False)
|
|
return
|
|
|
|
# saves changes to the function itself
|
|
def after_function_save(self, tile, request):
|
|
raise NotImplementedError
|
|
|