Esta documentación está en fase de desarrollo y puede contener errores.

MyDinaup

La librería .NET generada a partir del esquema de tu organización: secciones, informes y documentos convertidos en clases tipadas.

MyDinaup es una librería .NET que Dinaup genera a partir del esquema de tu organización: cada sección, informe y documento de tu tenant se convierte en una clase tipada con los nombres reales de tus campos.

Un tenant es tu instalación de Dinaup, con su propio modelo de datos. Ese modelo lo diseñas tú desde Dinaup Flex, así que dos organizaciones nunca tienen el mismo esquema. MyDinaup es el reflejo de tu esquema en código .NET.

El paquete se llama {Empresa}.MyDinaup. En este documento los ejemplos salen de DemoUp.MyDinaup, el modelo de pre-producción que usa el equipo de Dinaup, y las clases citadas son reales.

Qué problema resuelve

El SDK Dinaup habla con la API, pero no conoce tu esquema. Sin MyDinaup, identificas cada campo por su clave interna en crudo:

// Sin MyDinaup: claves de columna a pelo
var data = new Dictionary<string, string>
{
    { "pr_30655031", "SC-4471" },   // ¿qué campo es este?
    { "nombre", "Almacén central" }
};

Esas claves (pr_30655031, pr_506847515) no se adivinan, no se autocompletan y un error tipográfico no salta hasta que la petición falla en ejecución. MyDinaup pone un nombre legible a cada una y las expone como constantes:

// Con MyDinaup: nombres reales de tu esquema
using DemoUp.MyDinaup;

var data = new Dictionary<string, string>
{
    { SectionsD.AlmacenesD.AlmacenesES.SendcloudID, "SC-4471" },
    { SectionsD.AlmacenesD.AlmacenesES.TextoPrincipal, "Almacén central" }
};

Lo que ganas:

  • Tu esquema, tipado. Las clases llevan los nombres de tus secciones y campos, no los del modelo genérico.
  • Autocompletado. El editor sugiere secciones, campos e informes. No hace falta abrir Flex para recordar una clave.
  • Errores en compilación. Un campo mal escrito no compila. Sin MyDinaup, el mismo fallo es una excepción en tiempo de ejecución.
  • Filas fuertemente tipadas. Un informe devuelve row.Total As Decimal, no un diccionario de strings que conviertes a mano.

Qué contiene

MyDinaup depende del paquete Dinaup y añade tres grupos de clases, uno por cada tipo de objeto de tu esquema. Todas heredan de clases base que viven en el SDK.

Secciones

Una sección es una tabla de tu tenant: Almacenes, Entidades, Ventas. Por cada una, MyDinaup genera dos clases dentro de SectionsD:

  • {Seccion}ES: las claves de campo como constantes. AlmacenesES.SendcloudID devuelve la clave interna ("pr_30655031"). Úsala para construir filtros y WriteOperation.
  • {Seccion}C: la fila tipada, hereda de DinaupRowBase. Cada campo es una propiedad con su tipo real.
Public Class AlmacenesES
    Public Shared ReadOnly SendcloudID$ = "pr_30655031"
    Public Shared ReadOnly TextoPrincipal$ = "nombre"
    Public Shared ReadOnly FechaAlta_UTC$ = "pr_400105496714"
End Class

Public Class AlmacenesC
    Inherits DinaupRowBase
    Public Property SendcloudID As String
    Public Property FechaAlta_UTC As DateTime?
    Public Property ReferenciaResponsable As Dinaup.DinaupBasicInformation
End Class

Un campo que apunta a otra sección (una relación) se tipa como DinaupBasicInformation: trae el ID, el texto principal y la imagen del registro relacionado sin una segunda consulta.

La clase {Seccion}D también expone _SectionIDGUID (el identificador de la sección) y métodos de lectura directa: GetRowByIdAsync y GetRowsAsync.

Leer con SectionsD recupera la sección entera más los textos de sus relaciones, así que es más costoso. Para volumen o rendimiento, usa Informes. SectionsD encaja en código que corre poco o en prototipos.

Informes

Un informe es una consulta tipada. MyDinaup genera una clase API{Nombre}C por informe, bajo Reports.{Categoria}D, que hereda de DinaupReportBase(Of RowC) del SDK. La clase de fila anidada lleva una propiedad por columna, ya con su tipo:

Public Class APIAlmacenesC
    Inherits dinaup.DinaupReportBase(Of APIAlmacenes_RowC)

    Public Class APIAlmacenes_RowC
        Public Property ID As Guid
        Public Property TextoPrincipal As String
        Public Property DisponibleEnTPV As Boolean
        Public Property Color As EnumTextoEstiloE
    End Class
End Class

Al generar la fila, MyDinaup convierte cada columna con una llamada a método del SDK según su tipo: .STR() para texto, .ToGuid() para identificadores, .BOOL() para booleanos, .ToDateTime_UTC() para fechas, .INT(0) para enteros y enums. Son extensiones del paquete Dinaup.

El informe generado tolera que falte una columna en la respuesta del servidor. Cada columna se lee tras comprobar que existe, y la propiedad TolerateMissingColumns (heredada de DinaupReportBase) decide qué pasa si falta alguna:

  • false (valor por defecto): una columna ausente lanza excepción y delata el desajuste entre modelo y servidor de inmediato.
  • true: las columnas que faltan se registran como aviso y sus propiedades quedan en su valor por defecto, para poder cargar el resto.

Documentos dinámicos

Un documento dinámico es un procedimiento con guion que corre en el servidor y devuelve HTML, JSON, PDF u otro formato: una factura, un email, un volcado JSON. MyDinaup genera una clase por documento bajo DynamicDocuments.{Categoria}D, heredera de DinaupDynamicDocumentBase, que solo guarda su identificador y su título:

Public Class SesionC
    Inherits DinaupDynamicDocumentBase
    Sub New()
        Me.ID = New Guid("73fd6203-3109-4572-8ad0-8c58702dd1a5")
        Me.Title = "Sesión"
    End Sub
End Class

Enumeraciones y constantes

Además de los tres grupos, MyDinaup genera dos archivos de apoyo:

  • Enumeraciones.vb: los tipos de lista de tu esquema como Enum de .NET (EnumTextoEstiloE, con Estilo1 = 1, Estilo2 = 2…). Los usan las filas que tienen campos de ese tipo.
  • Constants.vb: los catálogos de estados y tipos como valores predefinidos: cada estado de una venta, cada tipo de documento oficial, con su GUID y su etiqueta. Útil para filtrar o escribir sin copiar identificadores a mano.

El esquema documentado en el propio código

Las clases generadas no traen solo nombres: cada constante de campo lleva su comportamiento en el servidor como documentación XML, y cada sección incluye sus scripts como comentarios. Es la letra pequeña que antes obligaba a abrir Flex o a descubrirla a base de errores de la API.

Qué cuenta cada campo

El comentario XML de la constante aparece en el editor al pasar el cursor o autocompletar. Un campo real de la sección Proyectos:

''' <summary>
''' This field is related to the 'bd46bc13-...' section (Tipos de proyecto).
''' Auto-filled with Referencia dato: To Do (Siempre).
''' Auto-managed: filled and locked by the server, do not provide it.
''' Text field: up to 36 characters.
''' </summary>
Public Shared ReadOnly ReferenciaTipo$ = "pr_30010431914"

Lo que puede anunciar cada campo:

AnotaciónQué significa para tu código
This field is related to the '…' sectionEs una relación: escribe el GUID de un registro de esa sección.
Auto-filled with …El servidor lo rellena solo (con un campo de la sesión, un valor fijo o un dato de referencia). Si dice Siempre, no intentes pisarlo.
Auto-managed: filled and locked by the serverNo lo mandes en la escritura: lo pone y bloquea el servidor.
READ-ONLY: auto-calculated by the server from the section …Contador o suma calculada desde otra sección. Escribirlo no tiene efecto.
REST write policy: can be set when creating … read-only on updateSolo acepta valor en el alta; en actualizaciones se ignora o falla.
Read-only via REST: auto-set by the server, never writableCampos de sistema (id, fecha, eliminado…): nunca se escriben.
Required / UniqueObligatorio al crear, o sin duplicados en la sección.
Text field: up to N characters / Numeric size: …Tamaño máximo del texto o dígitos enteros y decimales admitidos.

Antes de construir una WriteOperation, un vistazo a estas anotaciones evita los dos fallos típicos: mandar campos que el servidor gestiona y omitir los obligatorios.

Los scripts de la sección, legibles

Debajo de las constantes, cada sección incluye un bloque COMPORTAMIENTO / SCRIPTS con la lógica que el servidor ejecuta sobre sus registros: validaciones antes de aceptar, campos que se derivan al cambiar un estado, botones que crean registros relacionados.

'  Script:  Estado cambiado
'  Cuando:  Campo cambiado
'  Codigo:
'      if C.ReferenciaEstado.Estado = S.Enums.estadotramite.pendiente
'          C.EnProceso = 1
'      else
'          C.EnProceso = 0
'          end

No es código que tu aplicación ejecute: es documentación de lo que pasará en el servidor cuando escribas en esa sección. Si una escritura por API devuelve un error de validación o un campo cambia de valor "solo", la explicación suele estar en este bloque. También es contexto directo para asistentes de IA que trabajen sobre tu repositorio: leen el comportamiento de la sección sin salir del código. La sintaxis de esos scripts es DinaScript, con el prefijo C. apuntando al registro en edición.

Cómo se genera y se actualiza

MyDinaup no se escribe: lo genera Dinaup Desktop leyendo tu esquema. Cuando cambias el modelo en Flex (añades un campo, creas una sección, modificas un informe) regeneras la librería para que el código vuelva a reflejar el esquema.

Entra con el usuario Sistema

Abre Dinaup Desktop con el usuario Sistema. La generación no está disponible para otros usuarios.

Genera

Ve a Configuración > Generar MyDinaup y pulsa Commit. Dinaup vuelca las clases actualizadas al repositorio de tu paquete MyDinaup.

Publica y actualiza la referencia

Publica el paquete y sube la versión en tu proyecto. MyDinaup fija la versión del SDK que le toca (por ejemplo Dinaup 10.15.0.*), así que actualiza los dos a la vez.

Si el esquema cambia y no regeneras, el modelo y el servidor se desincronizan: un informe puede pedir una columna que ya no existe. Ahí es donde entra TolerateMissingColumns. Regenerar es la solución de fondo.

Cómo se usa

Instala el SDK base y tu paquete MyDinaup:

dotnet add package Dinaup
dotnet add package Demoup.MyDinaup

Conecta el cliente y ejecuta un informe tipado. Las filas ya vienen convertidas:

using Dinaup;
using DemoUp.MyDinaup.Reports.FuncionalidadD;

var client = await DinaupClientC.ConnectAsync(
    endPoint: "https://api.dinaup.com/v2/tu-codigo",
    publicKey: "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
    secretKey: "tu-secret-key-aqui"
);

var report = new APIAlmacenesC();
await report.ExecuteQueryAsync(client, page: 1, resultsPerPage: 50);

foreach (var row in report.Rows)
{
    Console.WriteLine($"{row.TextoPrincipal}: {row.DisponibleEnTPV}");
}

Qué modelo elegir

No todos los proyectos usan el MyDinaup de su propia organización:

PaqueteCuándoNota
{Empresa}.MyDinaupAplicación atada a un tenant concretoLo generas tú desde Dinaup Desktop
ReadyToGo.MyDinaupDesarrollo compatible con varias organizacionesSolo modela la estructura Ready-To-Go
DemoUp.MyDinaupPruebas del equipo de DinaupPre-producción, desaconsejado en producción: puede traer errores

Límites

  • Nombres en español. Las clases y campos salen con los nombres de tu esquema, que suelen estar en español (APIVentasC, ProductosES). No es configurable: es un reflejo de tu modelo.
  • VB.NET generado. El código de la librería es VB.NET. Lo consumes igual desde C#; el idioma del paquete no condiciona el de tu aplicación.
  • Hay que regenerar a mano. No se sincroniza solo. Un cambio de esquema exige volver a Generar MyDinaup.
  • Solo {Empresa}.MyDinaup refleja tu tenant. ReadyToGo y DemoUp son modelos ajenos a tu esquema.

Para el recetario de conexión, lectura, escritura y ejemplos, ver SDK .NET y API y el Cliente Dinaup.

On this page