Mapowanie danych między JSONami

0

Cześć, mam sytuację, w której są 2 aplikacje. W pierwszej generowany jest formularz w Formly, gdzie od API dostaje front dane w postaci JSONa, którymi można wypełnić część tego formularza. Powiedzmy, że jest to taki JSON, który przechowuje informacje imię, nazwisko oraz w addData lokacje swoich mieszkań :

{
    "name": "Jan",
    "surname": "Kowalski",
    "addData": [
        {
            "location": "Warszawa",
            "address": "Siemanowa 16"
        }
    ]
}

No i jest druga aplikacja, która chciałaby skorzystać z tej funkcjonalności formularza, i przesyła JSONa, ale jego nazwy kluczy są inne:

{
    "imie": "Jan",
    "nazwisko": "Kowalski",
    "dodatkoweInformacje": [
        {
            "lokacja": "Warszawa",
            "adres": "Siemanowa 16"
        },
        {
            "lokacja": "Kraków",
            "adres": "Miodowa 16"
        }
    ]
}

Co mógłbym zrobić, żeby zamienić nazwy kluczy drugiego JSONa na tego pierwszego? myślałem o użyciu słowników na zasadzie, że miałbym dodatkowy plik template'owy, gdzie np.
("name" : "ścieżkaDoImieWDrugimJsonie"}, po czym funkcją przypisywał wartość z tego jsona. Problem pojawiłby się przy sekcjach powielanych, gdzie jak u góry dodatkoweInformacje jest tablicą i ma 2 elementy(i może mieć więcej), natomiast pusty plik template'owy zawierałby tylko 1 element, więc byłby problem ze ścieżkami. Jak podejść do tego? Stack Angular+ .net core

0

Jeśli masz klasę, która reprezentuje twój obiekt w JSON to może dodać atrybuty po stronie .NET Core

public class Person
{
    [JsonProperty("imie")]
    public string Name { get; set; }

    [JsonProperty("nazwisko")]
    public string Surname { get; set; }
}

Po której stronie potrzebujesz to przerobić? Po stronie .NET Core czy Angulara?

0

@AdamWox: Po stronie .Net Core, ogólnie w pierwszej aplikacji nie mam klasy, gdyż jest to json na 400-500 pól, natomiast z drugiej aplikacji może przyjść tak z 30-40 pól

0

I masz zamiar faktycznie całego JSONa parsować ręcznie? Nie masz zamiaru deserializować tego jak cywilizowany człowiek? Od kiedy ilość pól decyduje o stworzeniu klasy? Masz zamiar korzystać ze wszystkich 400-500 pól? Zrób klasę tylko z tymi polami, które potrzebujesz, nie musisz mieć wszystkich. Oba API są twoje? Jeśli nie to po co ci .NET Core?

0

Jeśli miałoby to przychodzić te 30-40pól, nie byłoby problemu na sztywno to napisać. API pierwszej aplikacji jest moje, to do wysyłania formularza. Drugie natomiast jest już nie moje i nie mogę wymusić na nim przesyłania tak samo nazwanych zmiennych. O ile w pierwszej aplikacji można korzystać z tych 400-500pól, tak druga przesyła tylko 30-40

0

Wydaje mi się, że patrzę na twój problem przez pryzmat mojego programowania i nie widzę sensu w tym co tutaj piszesz. Nie poddaje się i spróbuje zrozumieć.

API_1 (twoje .NET Core) wysyła wstępne dane do formularza -> Angular ten formularz wyświetla i pozwala na zmiany -> API_2 dostaje formularz z Angulara. A problemem jest to, że twoje API_1 wysyła obiekt JSON w języku polskim, a API_2 potrzebuje tego w języku angielskim? Ciekawi mnie również czego tyczą się te obiekty JSON skoro mają 400-500 pól.

Czy jesteś w stanie pominąć swoje .NET Core i ogarnąć formularz w samym Angularze? Czy API_2 posiada dane, którymi musisz zainicjować formularz?

0

Ogólnie to API jest robione pod funkcjonalność, gdzie dwie aplikacje(desktopowa i webowa), mogą przesłać do niego dane, otwiera się formularz i po uzupełnieniu, dane wysyłane są do urzędu, a ta część danych poprawiona lub nie, wraca do aplikacji. Przy czym klucze w JSONie były przygotowane zgodnie z tym, co dostajemy z pierwszej aplikacji, a teraz doszła druga aplikacja, która również chce skorzystać z tej funkcjonalności i wysyła te dane, ale inaczej nazwane. Więc szukam sposobu na mapowanie, aby były one zgodne z już wcześniej przygotowanym JSONem.

0

Czyli jak rozumiem chcesz, żeby jeden endpoin obsłużył dwa różne JSONy (duży i mały ). Ja by wystawił dwa różne end pointy a w środku zrobił jedną logikę biznesową. W środku i tam musisz to wszystko serjalizować do obiektów to bym opakował mały obiekt dużym tak, żeby w logice biznesowej posługiwać się tylko jednym typem. Jak chcesz mieć jedne end point to jakoś musisz identyfikować typ jsona, który dostałeś i odpowiednio go serjalizować i potem opakować albo nie.

0

@UglyMan: dokładnie tak, tylko po prostu moje jeszcze małe umiejętności programistyczne szukały sposobu na zmianę tego małego JSONa na taki, który będzie czytany przez formularz

0

No pokaż co masz, co jest od ciebie zależne a co nie. Będzie łatwiej cos doradzić, bo tak to nie mam pojęcia co możesz a co nie. Ale ja bym raczej poszukał kogoś, kto ci pomoże to ogarnąć, bo sam możesz sobie zrobić krzywdę.

0
public class Person
{
    [JsonProperty("imie")]
    public string Name { get; set; }

    [JsonProperty("nazwisko")]
    public string Surname { get; set; }
}

Stoję w tym miejscu. Ogólnie to jest fajne rozwiązanie, tylko mam problem, bo pobieram sobie te pola, których nazwy są w JsonProperty i mam obiekt klasy Person z Name i Surname, git. Ale teraz gdybym z tego chciał utworzyć Jsona, aby był:

{
"name": "Jan",
"surname": "Kowalski
}

jest to możliwe? Czy mogę przy ponownej zmianie na JSONa ominąć JsonProperty, aby teraz utworzył się z kluczami name i surname?

1

Ja bym zrobił tak, że by zapakowałbym to w obiekt

public class Person2
{
   private Perscon _o;
   Person2(Person o){
   _o=o;
}
    public string Name { get => _o.Name ; set =>_o.Name = value ; }   
    public string Surname { get => _o.Surname ; set =>_o.Surname = value ;}
}

Nie to pozostaje ci ręczna zabawa z budowanie m Jsona.

0

Problem rozwiązany, do serializacji użyłem customowego ContractResolvera:

public class NameContractResolver : DefaultContractResolver
    {
        protected override IList<JsonProperty> CreateProperties(Type type, MemberSerialization memberSerialization)
        {
            IList<JsonProperty> list = base.CreateProperties(type, memberSerialization);
            string lowerCaseName;
            foreach (JsonProperty prop in list)
            {
                lowerCaseName= prop.UnderlyingName;
                prop.PropertyName =  char.ToLower(lowerCaseName[0]) + lowerCaseName.Substring(1);
            }
            return list;
        }

Dziękuję wszystkim za odpowiedzi :)

1 użytkowników online, w tym zalogowanych: 0, gości: 1