JSON är det textformat som har blivit väldigt populärt eftersom det är lätt att skriva och läsa för både människor och maskiner. XML var länge standardsättet att kommunicera med webbtjänster, men med JavaScripts intåg och dess inbyggda stöd för att konvertera mellan textformat och objekt har JSON blivit det absolut vanligaste formatet.
När vi läser eller skriver JSON är det i grund och botten strängar som hanteras. Som utvecklare av webbtjänster i Java behöver vi tolka förfrågningar och skicka svar. Data är ofta hårt typad och lagrad i POJOs (Plain Old Java Objects). Det är en standarduppgift: inget som ska ta för mycket tid att bygga, men som ändå måste fungera pålitligt och stabilt.
Jackson är ett trevligt bibliotek som kan hjälpa oss att lösa utmaningarna med att hantera JSON i Java. Med bara några rader kod kan vi omvandla ett objekt till en sträng redo att skickas över nätverket, eller läsa in en JSON-ström från en fil och omvandla den till ett objekt. Om du har arbetat med Spring Boot tidigare har du troligen redan stött på Jackson, eftersom det är standardbiblioteket för JSON-hantering där.
För att komma igång och arbeta med biblioteket behöver rätt beroenden läggas till Maven i pom.xml. Det går att hitta senaste på MVN Repository. I dag finns det huvudsakligen två versioner 1.x som inte aktivt utvecklas längre och version 2.x som är aktiv version. 3.x är under utveckling och kommer att släppas som ett eget paket (hösten 2025). När du bestämt vilken version du vill använda kan du kopiera rätt beroenden och lägga till dessa till pom.xml.
Kom igång
För att börja arbeta med biblioteket behöver rätt beroenden läggas till i pom.xml. Du hittar de senaste versionerna på MVN Repository.
I dag finns huvudsakligen två versioner:
1.x – inte längre aktivt utvecklad
2.x – den aktuella, aktivt utvecklade versionen
3.x – under utveckling, planeras släppas som eget paket (hösten 2025)
När du har bestämt vilken version du vill använda kan du kopiera beroenderaden och lägga till den i pom.xml:
Med hjälp av Jacksons databindings går det enkelt att konvertera mellan JSON och POJOs.
// Vi använder här en record istället för en klass
public record SuperHero(String name, int hp) { };
public static void testJackson() throws JsonProcessingException {
// Skapa en instans av ObjectMapper
ObjectMapper mapper = new ObjectMapper();
// Skapa en superhjälte med data
SuperHero superMan = new SuperHero(
"Superman",
2000
);
// Konvertera objektet till en JSON-sträng
String superManAsJson = mapper.writeValueAsString(superMan);
// Skriv ut resultatet på skärmen
System.out.println(superManAsJson);
// Skapa en sträng med JSON
String superHeroJson = "{ \"name\" : \"Cat Woman\", " +
"\"hp\" : 2002 }";
// Konvertera stränget till ett objekt
SuperHero catWoman = mapper.readValue(
superHeroJson,
SuperHero.class
);
// Skriv ut resultatet på skärmen
System.out.println(catWoman);
}
JSON som trädstruktur
Ibland har man JSON som behöver läsas in, men det finns ingen motsvarande klass. Då kan man istället läsa in datan som en trädstruktur.
// Konvertera JSON från sträng till nodes
JsonNode jsonNode = mapper.readTree(superHeroJson);
// Hämta ut värdena med hjälp av getters
String name = jsonNode.get("name").asText();
int hp = jsonNode.get("hp").asInt();
// Skriv ut resultatet på skärmen
System.out.println(
"SuperHero was: name = " + name +
" hp = " + hp
);
Hantering av filer
Om datan finns i filer går det bra att använda readValue och writeValue direkt mot en fil.
// Skriv objektet som en JSON-fil
mapper.writeValue(new File("out.json"), superMan);
// Läs in en fil till ett nytt objekt
SuperHero superManFromFile = mapper.readValue(
new File("out.json"),
SuperHero.class
);
Utöver detta går det även enkelt att arbeta med strömmar och byte-arrayer. Detta gör Jackson till ett smidigt och kraftfullt bibliotek.
Anpassning med annoteringar
En annan styrka med Jackson är flexibiliteten i hur konverteringen fungerar – både från objekt till JSON och från JSON till objekt.
Tänk dig att du har ett förbestämt JSON-format som inte matchar med namngivningen i din klass. Med Java-annoteringar kan detta anpassas.
Vi har en klass för skurkar, med name och damage. Dessutom kan skurkar ha hantlangare representerade av en Map<String, Villain>.
public class Villain {
private String name;
private int damage;
private Map<String, Villain> henchmen = new HashMap<>();
// Setters och Getters här
}
Men i vårt JSON-format heter damage istället strength. Dessutom representeras hantlangare som egna attribut. Exempel:
Vi kan lösa detta enkelt genom att arbeta med Jackson annoteringar. Med hjälp av @JsonGetteroch @JsonSetterkan vi styra hur klassen konverteras till och från JSON:
@JsonGetter("strength")
public int getDamage() {
return damage;
}
@JsonSetter("strength")
public void setDamage(int damage) {
this.damage = damage;
}
Damage kommer nu att heta strength både när JSON skapas eller omvandlas till objekt. Detta var enkelt. Nästa steg är att vi behöver hantera vår dörrvakt. Här kan vi använda @JsonAnySetteroch @JsonAnyGetter.
@JsonAnyGetter
public Map<String, Villain> getHenchmen() {
return henchmen;
}
// Notera att sätter tar emot nyckel/värde - inte hela
// map:en.
@JsonAnySetter
public void setHenchmen(String key, Villain villain){
this.henchmen.put(key, villain);
}
På detta sätt kan vi styra exakt hur konverteringen ska gå till. Jacksons ObjectMapper används som tidigare för att konvertera till och från JSON. Du kan hitta hela Villain.java här.
PHP är fortfarande år 2025 ett mycket populärt programmeringsspråk för att bygga webbapplikationer. Det är lättillgängligt, enkelt att hosta och relativt lätt att lära sig. Den största utmaningen som utvecklare är ofta att få en bra utvecklingsmiljö på plats. Ett vanligt tillvägagångssätt är att installera en färdigpaketerad miljö såsom MAMP, XAMPP eller WAMP. Jag är personligen inte särskilt förtjust i dessa lösningar eftersom de begränsar vilka versioner av de olika komponenterna du kan använda. Dessutom belastar dessa serverprogram datorn onödigt mycket.
Alternativet är att installera webbserver, MySQL och PHP var för sig och därefter konfigurera miljön manuellt. Det har vissa fördelar, såsom att hela PHP:s verktygskedja blir tillgänglig. Nackdelen är att det rör sig om flera program som kräver uppdatering och underhåll. Därför är jag inte heller helt nöjd med detta alternativ.
Ofta faller jag tillbaka till att använda Docker och köra applikationerna i containrar. Det gör det enkelt att skapa en miljö, uppdatera den och återskapa exakt samma miljö på en annan dator. Det enda som behöver installeras är Docker. Det är inte särskilt svårt, och med Docker följer dessutom Docker Compose, som är ett fantastiskt verktyg för att starta flera containrar samtidigt.
Docker desktop som har ett projekt med 5 körande containers
Innan vi fortsätter bör vi förklara vad avbildningar och containrar är. En avbildning är en mall för hur en virtuell maskin ska se ut – med operativsystem och alla installerade applikationer. En container är en körande instans av en avbildning. Det finns avbildningar för nästan alla applikationer du kan tänkas vilja köra. Ibland behöver en avbildning anpassas, vilket görs genom att skapa en ny avbildning som ärver från en befintlig version.
En avbildning kan skapas med hjälp av en Dockerfile.
# php.dockerfile
# Use php:8.2-apache as base image
FROM php:8.2-apache
# Install your extensions
# Add mysqli
RUN docker-php-ext-install mysqli
# Install pdo if you need to use PHP PDO
RUN docker-php-ext-install pdo pdo_mysql
# Run docker-php-ext-enable command to activate mysqli
RUN docker-php-ext-enable mysqli
I detta exempel skapar vi en egen avbildning baserad på PHP:s officiella avbildning. I denna finns Linux och en Apache-webbserver, men den saknar stöd för MySQL. Anpassningen innebär att vi installerar de komponenter som behövs (raderna 7 och 9) och till sist aktiverar vi den modul PHP behöver för att kommunicera med en MySQL-databas.
Vi kan bygga avbildningen med kommandot docker build. Därefter startar vi en container från avbildningen med kommandot docker start. Då är en enkel miljö igång men vi vill även ha en databas och några andra komponenter. Dessa kan också köras i Docker. När vi behöver flera avbildningar blir det snabbt krångligt att starta alla containrar manuellt. Här kommer Docker Compose in i bilden. Det läser in en annan fil, docker-compose.yml, och startar samt konfigurerar flera containrar åt oss. Enklare och smidigare. Låt oss titta på följande docker-compose.yml-fil:
Här definierar vi tre tjänster: PHP (rad 2-12), MySQL (rad 14-28) och phpMyAdmin (rad 30-41). Varje tjänst startas som en separat container. Vi definierar även volymer för datalagring och ett nätverk som containrarna kan använda för att kommunicera med varandra.
Låt oss titta närmare på en tjänstedefinition. Först specificeras vilken avbildning som ska användas. Det kan antingen vara en specifik avbildning, som mysql:latest, eller en build-sektion som beskriver hur en anpassad avbildning ska byggas – vilket vi gör med PHP.
Varje container behöver ett unikt namn. Man kan skapa flera instanser av samma avbildning, men varje instans måste ha ett unikt namn. Ofta behöver programvaran i containern konfigureras, och då är miljövariabler ett smidigt sätt. I MySQL (rad 19–22) och phpMyAdmin (rad 34–35) används miljövariabler som kan justeras vid behov. Här anges t.ex. vilka uppgifter som behövs för att ansluta till databasen.
Data i en container är inte beständig. Det är ett problem vid utveckling eftersom man vill kunna spara det man skapat. Genom att montera volymer i containern kan en yta utanför containern göras tillgänglig. För PHP (rad 8) monterar vi src-katalogen mot /var/www/html i containern (om katalogen inte finns kommer den att skapas). Då kan vi arbeta med filer i src och köra dem direkt via containern. Databasen använder en Docker-volym (raderna 24 samt 43–44), vilket är vanligt för binärdata som måste sparas.
Man kan bestämma vilka portar containrar ska exponera. För PHP mappas port 8080 på värddatorn mot port 80 i containern (rad 10). Det gör att vi kan surfa till localhost:8080 och komma åt webbservern. För databasen görs localhost:3306 tillgänglig (rad 26) och phpMyAdmin exponeras via port 8081 (rad 37). phpMyAdmin är ett populärt verktyg för att administrera MySQL-databaser.
Till sist ser vi att alla tjänster kopplas till nätverket app-network, vilket gör att de kan kommunicera med varandra. Det innebär t.ex. att ett PHP-script i PHP-containern kan ansluta till MySQL-containern.
Uppstart av flera containrar går fort
När konfigurationen är på plats kan du köra docker-compose up -d för att starta tjänsterna. Första gången tar det en stund eftersom avbildningarna laddas ner. Därefter går uppstarter snabbt. Du kan stoppa alla tjänster med kommandot docker-compose down eller via Docker Desktop.
Nu är allt klart. När tjänsterna är igång jobbar du med din PHP-kod i src-katalogen. Webbläsaren svarar på localhost:8080 och phpMyAdmin finns på localhost:8081.
Lycka till med din utveckling!
Nedladdningar
Du kan ladda ner mina filer här om du inte vill klipp och klistra:
PHP är fortfarande år 2025 ett mycket populärt programmeringsspråk för att bygga webbapplikationer. Det är lättillgängligt, enkelt att hosta och…
Kontakt
Kodkunskap är en plattform för alla programmerare – från nybörjare till erfarna utvecklare – som vill fördjupa sina kunskaper, dela insikter och växa tillsammans inom kodning och teknik.