[{"data":1,"prerenderedAt":4273},["ShallowReactive",2],{"post-java-security-best-practices":3,"rel-java-security-best-practices":954,"sib-java-security-best-practices":4201},{"_path":4,"_dir":5,"_draft":6,"_partial":6,"_locale":7,"title":8,"description":9,"date":10,"layout":11,"subtitle":12,"image":13,"optimized_image":13,"category":14,"tags":15,"author":20,"paginate":6,"body":21,"_type":948,"_id":949,"_source":950,"_file":951,"_stem":952,"_extension":953},"/posts/java-security-best-practices","posts",false,"","Java Security Best Practices: Preventing Vulnerabilities and Threats","Explore essential security strategies for Java applications, addressing common vulnerabilities identified by OWASP Top 10 with practical examples.","2024-08-15T11:00:00.000Z","post","Practical Strategies to Safeguard Your Java Applications","/assets/img/uploads/java-security-best-practices.png","code",[14,16,17,18,19],"java","security","owasp","cybersecurity","jaimedearcos",{"type":22,"children":23,"toc":936},"root",[24,36,43,48,103,108,114,119,256,261,267,272,380,386,391,514,519,525,530,555,560,566,571,587,592,598,603,686,691,697,702,822,827,833,838,871,876,882,887,894,930],{"type":25,"tag":26,"props":27,"children":28},"element","blockquote",{},[29],{"type":25,"tag":30,"props":31,"children":32},"p",{},[33],{"type":34,"value":35},"text","Security is critical in software development. Java applications, like all software, face numerous potential vulnerabilities. In this article, we will explore essential security best practices, referencing the OWASP Top 10, and providing practical Java examples to help you protect your applications effectively.",{"type":25,"tag":37,"props":38,"children":40},"h2",{"id":39},"understanding-owasp-top-10",[41],{"type":34,"value":42},"Understanding OWASP Top 10",{"type":25,"tag":30,"props":44,"children":45},{},[46],{"type":34,"value":47},"The OWASP Top 10 outlines the most critical web application security risks:",{"type":25,"tag":49,"props":50,"children":51},"ol",{},[52,58,63,68,73,78,83,88,93,98],{"type":25,"tag":53,"props":54,"children":55},"li",{},[56],{"type":34,"value":57},"Injection",{"type":25,"tag":53,"props":59,"children":60},{},[61],{"type":34,"value":62},"Broken Authentication",{"type":25,"tag":53,"props":64,"children":65},{},[66],{"type":34,"value":67},"Sensitive Data Exposure",{"type":25,"tag":53,"props":69,"children":70},{},[71],{"type":34,"value":72},"XML External Entities (XXE)",{"type":25,"tag":53,"props":74,"children":75},{},[76],{"type":34,"value":77},"Broken Access Control",{"type":25,"tag":53,"props":79,"children":80},{},[81],{"type":34,"value":82},"Security Misconfiguration",{"type":25,"tag":53,"props":84,"children":85},{},[86],{"type":34,"value":87},"Cross-Site Scripting (XSS)",{"type":25,"tag":53,"props":89,"children":90},{},[91],{"type":34,"value":92},"Insecure Deserialization",{"type":25,"tag":53,"props":94,"children":95},{},[96],{"type":34,"value":97},"Using Components with Known Vulnerabilities",{"type":25,"tag":53,"props":99,"children":100},{},[101],{"type":34,"value":102},"Insufficient Logging and Monitoring",{"type":25,"tag":30,"props":104,"children":105},{},[106],{"type":34,"value":107},"Let's delve into practical strategies and Java implementations for some of these threats.",{"type":25,"tag":37,"props":109,"children":111},{"id":110},"_1-injection-prevention",[112],{"type":34,"value":113},"1. Injection Prevention",{"type":25,"tag":30,"props":115,"children":116},{},[117],{"type":34,"value":118},"Use Prepared Statements and parameterized queries:",{"type":25,"tag":120,"props":121,"children":124},"pre",{"className":122,"code":123,"language":16,"meta":7,"style":7},"language-java shiki shiki-themes github-dark github-light","PreparedStatement stmt = connection.prepareStatement(\"SELECT * FROM users WHERE username=? AND password=?\");\nstmt.setString(1, username);\nstmt.setString(2, password);\nResultSet rs = stmt.executeQuery();\n",[125],{"type":25,"tag":14,"props":126,"children":127},{"__ignoreMap":7},[128,173,202,228],{"type":25,"tag":129,"props":130,"children":133},"span",{"class":131,"line":132},"line",1,[134,140,146,151,157,162,168],{"type":25,"tag":129,"props":135,"children":137},{"style":136},"--shiki-default:#E1E4E8;--shiki-light:#24292E",[138],{"type":34,"value":139},"PreparedStatement stmt ",{"type":25,"tag":129,"props":141,"children":143},{"style":142},"--shiki-default:#F97583;--shiki-light:#D73A49",[144],{"type":34,"value":145},"=",{"type":25,"tag":129,"props":147,"children":148},{"style":136},[149],{"type":34,"value":150}," connection.",{"type":25,"tag":129,"props":152,"children":154},{"style":153},"--shiki-default:#B392F0;--shiki-light:#6F42C1",[155],{"type":34,"value":156},"prepareStatement",{"type":25,"tag":129,"props":158,"children":159},{"style":136},[160],{"type":34,"value":161},"(",{"type":25,"tag":129,"props":163,"children":165},{"style":164},"--shiki-default:#9ECBFF;--shiki-light:#032F62",[166],{"type":34,"value":167},"\"SELECT * FROM users WHERE username=? AND password=?\"",{"type":25,"tag":129,"props":169,"children":170},{"style":136},[171],{"type":34,"value":172},");\n",{"type":25,"tag":129,"props":174,"children":176},{"class":131,"line":175},2,[177,182,187,191,197],{"type":25,"tag":129,"props":178,"children":179},{"style":136},[180],{"type":34,"value":181},"stmt.",{"type":25,"tag":129,"props":183,"children":184},{"style":153},[185],{"type":34,"value":186},"setString",{"type":25,"tag":129,"props":188,"children":189},{"style":136},[190],{"type":34,"value":161},{"type":25,"tag":129,"props":192,"children":194},{"style":193},"--shiki-default:#79B8FF;--shiki-light:#005CC5",[195],{"type":34,"value":196},"1",{"type":25,"tag":129,"props":198,"children":199},{"style":136},[200],{"type":34,"value":201},", username);\n",{"type":25,"tag":129,"props":203,"children":205},{"class":131,"line":204},3,[206,210,214,218,223],{"type":25,"tag":129,"props":207,"children":208},{"style":136},[209],{"type":34,"value":181},{"type":25,"tag":129,"props":211,"children":212},{"style":153},[213],{"type":34,"value":186},{"type":25,"tag":129,"props":215,"children":216},{"style":136},[217],{"type":34,"value":161},{"type":25,"tag":129,"props":219,"children":220},{"style":193},[221],{"type":34,"value":222},"2",{"type":25,"tag":129,"props":224,"children":225},{"style":136},[226],{"type":34,"value":227},", password);\n",{"type":25,"tag":129,"props":229,"children":231},{"class":131,"line":230},4,[232,237,241,246,251],{"type":25,"tag":129,"props":233,"children":234},{"style":136},[235],{"type":34,"value":236},"ResultSet rs ",{"type":25,"tag":129,"props":238,"children":239},{"style":142},[240],{"type":34,"value":145},{"type":25,"tag":129,"props":242,"children":243},{"style":136},[244],{"type":34,"value":245}," stmt.",{"type":25,"tag":129,"props":247,"children":248},{"style":153},[249],{"type":34,"value":250},"executeQuery",{"type":25,"tag":129,"props":252,"children":253},{"style":136},[254],{"type":34,"value":255},"();\n",{"type":25,"tag":30,"props":257,"children":258},{},[259],{"type":34,"value":260},"This approach prevents SQL injection by ensuring that input data is treated as data, not executable code.",{"type":25,"tag":37,"props":262,"children":264},{"id":263},"_2-secure-authentication",[265],{"type":34,"value":266},"2. Secure Authentication",{"type":25,"tag":30,"props":268,"children":269},{},[270],{"type":34,"value":271},"Implement robust authentication using secure password storage (bcrypt or Argon2):",{"type":25,"tag":120,"props":273,"children":275},{"className":122,"code":274,"language":16,"meta":7,"style":7},"import org.springframework.security.crypto.bcrypt.BCrypt;\n\nString hashedPassword = BCrypt.hashpw(password, BCrypt.gensalt());\nif (BCrypt.checkpw(password, hashedPassword)) {\n    // authentication successful\n}\n",[276],{"type":25,"tag":14,"props":277,"children":278},{"__ignoreMap":7},[279,292,301,338,361,371],{"type":25,"tag":129,"props":280,"children":281},{"class":131,"line":132},[282,287],{"type":25,"tag":129,"props":283,"children":284},{"style":142},[285],{"type":34,"value":286},"import",{"type":25,"tag":129,"props":288,"children":289},{"style":136},[290],{"type":34,"value":291}," org.springframework.security.crypto.bcrypt.BCrypt;\n",{"type":25,"tag":129,"props":293,"children":294},{"class":131,"line":175},[295],{"type":25,"tag":129,"props":296,"children":298},{"emptyLinePlaceholder":297},true,[299],{"type":34,"value":300},"\n",{"type":25,"tag":129,"props":302,"children":303},{"class":131,"line":204},[304,309,313,318,323,328,333],{"type":25,"tag":129,"props":305,"children":306},{"style":136},[307],{"type":34,"value":308},"String hashedPassword ",{"type":25,"tag":129,"props":310,"children":311},{"style":142},[312],{"type":34,"value":145},{"type":25,"tag":129,"props":314,"children":315},{"style":136},[316],{"type":34,"value":317}," BCrypt.",{"type":25,"tag":129,"props":319,"children":320},{"style":153},[321],{"type":34,"value":322},"hashpw",{"type":25,"tag":129,"props":324,"children":325},{"style":136},[326],{"type":34,"value":327},"(password, BCrypt.",{"type":25,"tag":129,"props":329,"children":330},{"style":153},[331],{"type":34,"value":332},"gensalt",{"type":25,"tag":129,"props":334,"children":335},{"style":136},[336],{"type":34,"value":337},"());\n",{"type":25,"tag":129,"props":339,"children":340},{"class":131,"line":230},[341,346,351,356],{"type":25,"tag":129,"props":342,"children":343},{"style":142},[344],{"type":34,"value":345},"if",{"type":25,"tag":129,"props":347,"children":348},{"style":136},[349],{"type":34,"value":350}," (BCrypt.",{"type":25,"tag":129,"props":352,"children":353},{"style":153},[354],{"type":34,"value":355},"checkpw",{"type":25,"tag":129,"props":357,"children":358},{"style":136},[359],{"type":34,"value":360},"(password, hashedPassword)) {\n",{"type":25,"tag":129,"props":362,"children":364},{"class":131,"line":363},5,[365],{"type":25,"tag":129,"props":366,"children":368},{"style":367},"--shiki-default:#6A737D;--shiki-light:#6A737D",[369],{"type":34,"value":370},"    // authentication successful\n",{"type":25,"tag":129,"props":372,"children":374},{"class":131,"line":373},6,[375],{"type":25,"tag":129,"props":376,"children":377},{"style":136},[378],{"type":34,"value":379},"}\n",{"type":25,"tag":37,"props":381,"children":383},{"id":382},"_3-sensitive-data-exposure",[384],{"type":34,"value":385},"3. Sensitive Data Exposure",{"type":25,"tag":30,"props":387,"children":388},{},[389],{"type":34,"value":390},"Use encryption for sensitive data storage:",{"type":25,"tag":120,"props":392,"children":394},{"className":122,"code":393,"language":16,"meta":7,"style":7},"Cipher cipher = Cipher.getInstance(\"AES/GCM/NoPadding\");\nSecretKey key = generateSecretKey();\ncipher.init(Cipher.ENCRYPT_MODE, key);\nbyte[] encryptedData = cipher.doFinal(plainData.getBytes(StandardCharsets.UTF_8));\n",[395],{"type":25,"tag":14,"props":396,"children":397},{"__ignoreMap":7},[398,433,454,472],{"type":25,"tag":129,"props":399,"children":400},{"class":131,"line":132},[401,406,410,415,420,424,429],{"type":25,"tag":129,"props":402,"children":403},{"style":136},[404],{"type":34,"value":405},"Cipher cipher ",{"type":25,"tag":129,"props":407,"children":408},{"style":142},[409],{"type":34,"value":145},{"type":25,"tag":129,"props":411,"children":412},{"style":136},[413],{"type":34,"value":414}," Cipher.",{"type":25,"tag":129,"props":416,"children":417},{"style":153},[418],{"type":34,"value":419},"getInstance",{"type":25,"tag":129,"props":421,"children":422},{"style":136},[423],{"type":34,"value":161},{"type":25,"tag":129,"props":425,"children":426},{"style":164},[427],{"type":34,"value":428},"\"AES/GCM/NoPadding\"",{"type":25,"tag":129,"props":430,"children":431},{"style":136},[432],{"type":34,"value":172},{"type":25,"tag":129,"props":434,"children":435},{"class":131,"line":175},[436,441,445,450],{"type":25,"tag":129,"props":437,"children":438},{"style":136},[439],{"type":34,"value":440},"SecretKey key ",{"type":25,"tag":129,"props":442,"children":443},{"style":142},[444],{"type":34,"value":145},{"type":25,"tag":129,"props":446,"children":447},{"style":153},[448],{"type":34,"value":449}," generateSecretKey",{"type":25,"tag":129,"props":451,"children":452},{"style":136},[453],{"type":34,"value":255},{"type":25,"tag":129,"props":455,"children":456},{"class":131,"line":204},[457,462,467],{"type":25,"tag":129,"props":458,"children":459},{"style":136},[460],{"type":34,"value":461},"cipher.",{"type":25,"tag":129,"props":463,"children":464},{"style":153},[465],{"type":34,"value":466},"init",{"type":25,"tag":129,"props":468,"children":469},{"style":136},[470],{"type":34,"value":471},"(Cipher.ENCRYPT_MODE, key);\n",{"type":25,"tag":129,"props":473,"children":474},{"class":131,"line":230},[475,480,485,489,494,499,504,509],{"type":25,"tag":129,"props":476,"children":477},{"style":142},[478],{"type":34,"value":479},"byte",{"type":25,"tag":129,"props":481,"children":482},{"style":136},[483],{"type":34,"value":484},"[] encryptedData ",{"type":25,"tag":129,"props":486,"children":487},{"style":142},[488],{"type":34,"value":145},{"type":25,"tag":129,"props":490,"children":491},{"style":136},[492],{"type":34,"value":493}," cipher.",{"type":25,"tag":129,"props":495,"children":496},{"style":153},[497],{"type":34,"value":498},"doFinal",{"type":25,"tag":129,"props":500,"children":501},{"style":136},[502],{"type":34,"value":503},"(plainData.",{"type":25,"tag":129,"props":505,"children":506},{"style":153},[507],{"type":34,"value":508},"getBytes",{"type":25,"tag":129,"props":510,"children":511},{"style":136},[512],{"type":34,"value":513},"(StandardCharsets.UTF_8));\n",{"type":25,"tag":30,"props":515,"children":516},{},[517],{"type":34,"value":518},"Always encrypt data at rest and in transit (use HTTPS).",{"type":25,"tag":37,"props":520,"children":522},{"id":521},"_4-security-misconfiguration",[523],{"type":34,"value":524},"4. Security Misconfiguration",{"type":25,"tag":30,"props":526,"children":527},{},[528],{"type":34,"value":529},"Adopt secure defaults, disable debugging, and avoid detailed error messages:",{"type":25,"tag":120,"props":531,"children":535},{"className":532,"code":533,"language":534,"meta":7,"style":7},"language-properties shiki shiki-themes github-dark github-light","server.error.include-stacktrace=never\nserver.error.include-message=never\n","properties",[536],{"type":25,"tag":14,"props":537,"children":538},{"__ignoreMap":7},[539,547],{"type":25,"tag":129,"props":540,"children":541},{"class":131,"line":132},[542],{"type":25,"tag":129,"props":543,"children":544},{},[545],{"type":34,"value":546},"server.error.include-stacktrace=never\n",{"type":25,"tag":129,"props":548,"children":549},{"class":131,"line":175},[550],{"type":25,"tag":129,"props":551,"children":552},{},[553],{"type":34,"value":554},"server.error.include-message=never\n",{"type":25,"tag":30,"props":556,"children":557},{},[558],{"type":34,"value":559},"Review and secure your Java application configuration regularly.",{"type":25,"tag":37,"props":561,"children":563},{"id":562},"_5-cross-site-scripting-xss",[564],{"type":34,"value":565},"5. Cross-Site Scripting (XSS)",{"type":25,"tag":30,"props":567,"children":568},{},[569],{"type":34,"value":570},"Utilize proper encoding or frameworks that prevent XSS by default, such as Thymeleaf:",{"type":25,"tag":120,"props":572,"children":576},{"className":573,"code":574,"language":575,"meta":7,"style":7},"language-html shiki shiki-themes github-dark github-light","\u003Cp th:text=\"${userInput}\">\u003C/p>\n","html",[577],{"type":25,"tag":14,"props":578,"children":579},{"__ignoreMap":7},[580],{"type":25,"tag":129,"props":581,"children":582},{"class":131,"line":132},[583],{"type":25,"tag":129,"props":584,"children":585},{},[586],{"type":34,"value":574},{"type":25,"tag":30,"props":588,"children":589},{},[590],{"type":34,"value":591},"Avoid directly inserting user inputs into HTML without proper sanitization or encoding.",{"type":25,"tag":37,"props":593,"children":595},{"id":594},"_6-insecure-deserialization",[596],{"type":34,"value":597},"6. Insecure Deserialization",{"type":25,"tag":30,"props":599,"children":600},{},[601],{"type":34,"value":602},"Limit deserialization to trusted sources only:",{"type":25,"tag":120,"props":604,"children":606},{"className":122,"code":605,"language":16,"meta":7,"style":7},"ObjectInputStream ois = new ObjectInputStream(new FileInputStream(\"trusted_data.ser\"));\nMyObject obj = (MyObject) ois.readObject();\n",[607],{"type":25,"tag":14,"props":608,"children":609},{"__ignoreMap":7},[610,660],{"type":25,"tag":129,"props":611,"children":612},{"class":131,"line":132},[613,618,622,627,632,636,641,646,650,655],{"type":25,"tag":129,"props":614,"children":615},{"style":136},[616],{"type":34,"value":617},"ObjectInputStream ois ",{"type":25,"tag":129,"props":619,"children":620},{"style":142},[621],{"type":34,"value":145},{"type":25,"tag":129,"props":623,"children":624},{"style":142},[625],{"type":34,"value":626}," new",{"type":25,"tag":129,"props":628,"children":629},{"style":153},[630],{"type":34,"value":631}," ObjectInputStream",{"type":25,"tag":129,"props":633,"children":634},{"style":136},[635],{"type":34,"value":161},{"type":25,"tag":129,"props":637,"children":638},{"style":142},[639],{"type":34,"value":640},"new",{"type":25,"tag":129,"props":642,"children":643},{"style":153},[644],{"type":34,"value":645}," FileInputStream",{"type":25,"tag":129,"props":647,"children":648},{"style":136},[649],{"type":34,"value":161},{"type":25,"tag":129,"props":651,"children":652},{"style":164},[653],{"type":34,"value":654},"\"trusted_data.ser\"",{"type":25,"tag":129,"props":656,"children":657},{"style":136},[658],{"type":34,"value":659},"));\n",{"type":25,"tag":129,"props":661,"children":662},{"class":131,"line":175},[663,668,672,677,682],{"type":25,"tag":129,"props":664,"children":665},{"style":136},[666],{"type":34,"value":667},"MyObject obj ",{"type":25,"tag":129,"props":669,"children":670},{"style":142},[671],{"type":34,"value":145},{"type":25,"tag":129,"props":673,"children":674},{"style":136},[675],{"type":34,"value":676}," (MyObject) ois.",{"type":25,"tag":129,"props":678,"children":679},{"style":153},[680],{"type":34,"value":681},"readObject",{"type":25,"tag":129,"props":683,"children":684},{"style":136},[685],{"type":34,"value":255},{"type":25,"tag":30,"props":687,"children":688},{},[689],{"type":34,"value":690},"Always validate deserialized data.",{"type":25,"tag":37,"props":692,"children":694},{"id":693},"_7-component-vulnerabilities",[695],{"type":34,"value":696},"7. Component Vulnerabilities",{"type":25,"tag":30,"props":698,"children":699},{},[700],{"type":34,"value":701},"Regularly update libraries and dependencies, and use tools like OWASP Dependency-Check to identify vulnerabilities:",{"type":25,"tag":120,"props":703,"children":707},{"className":704,"code":705,"language":706,"meta":7,"style":7},"language-xml shiki shiki-themes github-dark github-light","\u003Cplugin>\n    \u003CgroupId>org.owasp\u003C/groupId>\n    \u003CartifactId>dependency-check-maven\u003C/artifactId>\n    \u003Cversion>9.0.9\u003C/version>\n\u003C/plugin>\n","xml",[708],{"type":25,"tag":14,"props":709,"children":710},{"__ignoreMap":7},[711,730,756,781,806],{"type":25,"tag":129,"props":712,"children":713},{"class":131,"line":132},[714,719,725],{"type":25,"tag":129,"props":715,"children":716},{"style":136},[717],{"type":34,"value":718},"\u003C",{"type":25,"tag":129,"props":720,"children":722},{"style":721},"--shiki-default:#85E89D;--shiki-light:#22863A",[723],{"type":34,"value":724},"plugin",{"type":25,"tag":129,"props":726,"children":727},{"style":136},[728],{"type":34,"value":729},">\n",{"type":25,"tag":129,"props":731,"children":732},{"class":131,"line":175},[733,738,743,748,752],{"type":25,"tag":129,"props":734,"children":735},{"style":136},[736],{"type":34,"value":737},"    \u003C",{"type":25,"tag":129,"props":739,"children":740},{"style":721},[741],{"type":34,"value":742},"groupId",{"type":25,"tag":129,"props":744,"children":745},{"style":136},[746],{"type":34,"value":747},">org.owasp\u003C/",{"type":25,"tag":129,"props":749,"children":750},{"style":721},[751],{"type":34,"value":742},{"type":25,"tag":129,"props":753,"children":754},{"style":136},[755],{"type":34,"value":729},{"type":25,"tag":129,"props":757,"children":758},{"class":131,"line":204},[759,763,768,773,777],{"type":25,"tag":129,"props":760,"children":761},{"style":136},[762],{"type":34,"value":737},{"type":25,"tag":129,"props":764,"children":765},{"style":721},[766],{"type":34,"value":767},"artifactId",{"type":25,"tag":129,"props":769,"children":770},{"style":136},[771],{"type":34,"value":772},">dependency-check-maven\u003C/",{"type":25,"tag":129,"props":774,"children":775},{"style":721},[776],{"type":34,"value":767},{"type":25,"tag":129,"props":778,"children":779},{"style":136},[780],{"type":34,"value":729},{"type":25,"tag":129,"props":782,"children":783},{"class":131,"line":230},[784,788,793,798,802],{"type":25,"tag":129,"props":785,"children":786},{"style":136},[787],{"type":34,"value":737},{"type":25,"tag":129,"props":789,"children":790},{"style":721},[791],{"type":34,"value":792},"version",{"type":25,"tag":129,"props":794,"children":795},{"style":136},[796],{"type":34,"value":797},">9.0.9\u003C/",{"type":25,"tag":129,"props":799,"children":800},{"style":721},[801],{"type":34,"value":792},{"type":25,"tag":129,"props":803,"children":804},{"style":136},[805],{"type":34,"value":729},{"type":25,"tag":129,"props":807,"children":808},{"class":131,"line":363},[809,814,818],{"type":25,"tag":129,"props":810,"children":811},{"style":136},[812],{"type":34,"value":813},"\u003C/",{"type":25,"tag":129,"props":815,"children":816},{"style":721},[817],{"type":34,"value":724},{"type":25,"tag":129,"props":819,"children":820},{"style":136},[821],{"type":34,"value":729},{"type":25,"tag":30,"props":823,"children":824},{},[825],{"type":34,"value":826},"Execute dependency checks regularly in your CI/CD pipeline.",{"type":25,"tag":37,"props":828,"children":830},{"id":829},"_8-logging-and-monitoring",[831],{"type":34,"value":832},"8. Logging and Monitoring",{"type":25,"tag":30,"props":834,"children":835},{},[836],{"type":34,"value":837},"Implement comprehensive logging and monitoring to detect and respond to security incidents:",{"type":25,"tag":120,"props":839,"children":841},{"className":122,"code":840,"language":16,"meta":7,"style":7},"logger.warn(\"Failed login attempt for user: {}\", username);\n",[842],{"type":25,"tag":14,"props":843,"children":844},{"__ignoreMap":7},[845],{"type":25,"tag":129,"props":846,"children":847},{"class":131,"line":132},[848,853,858,862,867],{"type":25,"tag":129,"props":849,"children":850},{"style":136},[851],{"type":34,"value":852},"logger.",{"type":25,"tag":129,"props":854,"children":855},{"style":153},[856],{"type":34,"value":857},"warn",{"type":25,"tag":129,"props":859,"children":860},{"style":136},[861],{"type":34,"value":161},{"type":25,"tag":129,"props":863,"children":864},{"style":164},[865],{"type":34,"value":866},"\"Failed login attempt for user: {}\"",{"type":25,"tag":129,"props":868,"children":869},{"style":136},[870],{"type":34,"value":201},{"type":25,"tag":30,"props":872,"children":873},{},[874],{"type":34,"value":875},"Aggregate logs centrally, and set up alerts for suspicious activities.",{"type":25,"tag":37,"props":877,"children":879},{"id":878},"conclusion",[880],{"type":34,"value":881},"Conclusion",{"type":25,"tag":30,"props":883,"children":884},{},[885],{"type":34,"value":886},"Adopting these best practices can greatly enhance the security posture of your Java applications. Stay proactive by regularly reviewing security measures, updating dependencies, and monitoring your systems. Security is a continuous process, not a one-time setup.",{"type":25,"tag":888,"props":889,"children":891},"h1",{"id":890},"further-reading",[892],{"type":34,"value":893},"Further Reading",{"type":25,"tag":895,"props":896,"children":897},"ul",{},[898,910,920],{"type":25,"tag":53,"props":899,"children":900},{},[901],{"type":25,"tag":902,"props":903,"children":907},"a",{"href":904,"rel":905},"https://owasp.org/www-project-top-ten/",[906],"nofollow",[908],{"type":34,"value":909},"OWASP Top 10",{"type":25,"tag":53,"props":911,"children":912},{},[913],{"type":25,"tag":902,"props":914,"children":917},{"href":915,"rel":916},"https://spring.io/projects/spring-security",[906],[918],{"type":34,"value":919},"Spring Security",{"type":25,"tag":53,"props":921,"children":922},{},[923],{"type":25,"tag":902,"props":924,"children":927},{"href":925,"rel":926},"https://owasp.org/www-project-dependency-check/",[906],[928],{"type":34,"value":929},"OWASP Dependency Check",{"type":25,"tag":931,"props":932,"children":933},"style",{},[934],{"type":34,"value":935},"html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html.light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}",{"title":7,"searchDepth":175,"depth":175,"links":937},[938,939,940,941,942,943,944,945,946,947],{"id":39,"depth":175,"text":42},{"id":110,"depth":175,"text":113},{"id":263,"depth":175,"text":266},{"id":382,"depth":175,"text":385},{"id":521,"depth":175,"text":524},{"id":562,"depth":175,"text":565},{"id":594,"depth":175,"text":597},{"id":693,"depth":175,"text":696},{"id":829,"depth":175,"text":832},{"id":878,"depth":175,"text":881},"markdown","content:posts:java-security-best-practices.md","content","posts/java-security-best-practices.md","posts/java-security-best-practices","md",[955,2371,3191],{"_path":956,"_dir":5,"_draft":6,"_partial":6,"_locale":7,"title":957,"description":958,"date":959,"layout":11,"subtitle":960,"image":961,"optimized_image":961,"category":14,"tags":962,"author":20,"paginate":6,"body":968,"_type":948,"_id":2368,"_source":950,"_file":2369,"_stem":2370,"_extension":953},"/posts/gpt-sql-integration","Implementa un analizador de consultas en lenguaje natural para bases de datos SQL con GPT","Aprende a implementar un sistema que convierte consultas en lenguaje natural en sentencias SQL usando OpenAI GPT, con un tutorial paso a paso y ejemplos prácticos.","2025-01-15T11:00:00.000Z","Transforma preguntas naturales en consultas SQL automatizadas","/assets/img/uploads/gpt-sql-integration.png",[14,963,964,965,966,967],"gpt","openai","sql","ai","nlp",{"type":22,"children":969,"toc":2357},[970,978,984,1002,1008,1013,1055,1068,1084,1090,1095,1309,1315,1320,1656,1662,1667,2018,2024,2029,2088,2094,2099,2279,2285,2303,2309,2314,2320,2353],{"type":25,"tag":26,"props":971,"children":972},{},[973],{"type":25,"tag":30,"props":974,"children":975},{},[976],{"type":34,"value":977},"Convertir preguntas naturales en consultas SQL de forma automática simplifica la interacción con bases de datos, permitiendo que usuarios sin conocimientos técnicos extraigan datos relevantes. En este tutorial, aprenderás a implementar esta solución utilizando la API de OpenAI GPT.",{"type":25,"tag":37,"props":979,"children":981},{"id":980},"requisitos-previos",[982],{"type":34,"value":983},"Requisitos Previos",{"type":25,"tag":895,"props":985,"children":986},{},[987,992,997],{"type":25,"tag":53,"props":988,"children":989},{},[990],{"type":34,"value":991},"Cuenta y clave API de OpenAI",{"type":25,"tag":53,"props":993,"children":994},{},[995],{"type":34,"value":996},"Python instalado en tu entorno",{"type":25,"tag":53,"props":998,"children":999},{},[1000],{"type":34,"value":1001},"Base de datos SQL (ej.: PostgreSQL, MySQL)",{"type":25,"tag":37,"props":1003,"children":1005},{"id":1004},"paso-1-configuración-del-entorno",[1006],{"type":34,"value":1007},"Paso 1: Configuración del entorno",{"type":25,"tag":30,"props":1009,"children":1010},{},[1011],{"type":34,"value":1012},"Primero, instala las dependencias necesarias:",{"type":25,"tag":120,"props":1014,"children":1018},{"className":1015,"code":1016,"language":1017,"meta":7,"style":7},"language-bash shiki shiki-themes github-dark github-light","pip install openai python-dotenv sqlalchemy psycopg2-binary\n","bash",[1019],{"type":25,"tag":14,"props":1020,"children":1021},{"__ignoreMap":7},[1022],{"type":25,"tag":129,"props":1023,"children":1024},{"class":131,"line":132},[1025,1030,1035,1040,1045,1050],{"type":25,"tag":129,"props":1026,"children":1027},{"style":153},[1028],{"type":34,"value":1029},"pip",{"type":25,"tag":129,"props":1031,"children":1032},{"style":164},[1033],{"type":34,"value":1034}," install",{"type":25,"tag":129,"props":1036,"children":1037},{"style":164},[1038],{"type":34,"value":1039}," openai",{"type":25,"tag":129,"props":1041,"children":1042},{"style":164},[1043],{"type":34,"value":1044}," python-dotenv",{"type":25,"tag":129,"props":1046,"children":1047},{"style":164},[1048],{"type":34,"value":1049}," sqlalchemy",{"type":25,"tag":129,"props":1051,"children":1052},{"style":164},[1053],{"type":34,"value":1054}," psycopg2-binary\n",{"type":25,"tag":30,"props":1056,"children":1057},{},[1058,1060,1066],{"type":34,"value":1059},"Guarda tu clave API en un archivo ",{"type":25,"tag":14,"props":1061,"children":1063},{"className":1062},[],[1064],{"type":34,"value":1065},".env",{"type":34,"value":1067},":",{"type":25,"tag":120,"props":1069,"children":1073},{"className":1070,"code":1071,"language":1072,"meta":7,"style":7},"language-env shiki shiki-themes github-dark github-light","OPENAI_API_KEY='tu-api-key'\n","env",[1074],{"type":25,"tag":14,"props":1075,"children":1076},{"__ignoreMap":7},[1077],{"type":25,"tag":129,"props":1078,"children":1079},{"class":131,"line":132},[1080],{"type":25,"tag":129,"props":1081,"children":1082},{},[1083],{"type":34,"value":1071},{"type":25,"tag":37,"props":1085,"children":1087},{"id":1086},"paso-2-conexión-a-la-base-de-datos",[1088],{"type":34,"value":1089},"Paso 2: Conexión a la base de datos",{"type":25,"tag":30,"props":1091,"children":1092},{},[1093],{"type":34,"value":1094},"Utiliza SQLAlchemy para conectarte a tu base de datos:",{"type":25,"tag":120,"props":1096,"children":1100},{"className":1097,"code":1098,"language":1099,"meta":7,"style":7},"language-python shiki shiki-themes github-dark github-light","from sqlalchemy import create_engine\nfrom sqlalchemy.orm import sessionmaker\nimport os\nfrom dotenv import load_dotenv\n\nload_dotenv()\n\nDATABASE_URL = os.getenv(\"DATABASE_URL\")\nengine = create_engine(DATABASE_URL)\nSession = sessionmaker(bind=engine)\nsession = Session()\n","python",[1101],{"type":25,"tag":14,"props":1102,"children":1103},{"__ignoreMap":7},[1104,1126,1147,1159,1180,1187,1195,1203,1232,1258,1291],{"type":25,"tag":129,"props":1105,"children":1106},{"class":131,"line":132},[1107,1112,1117,1121],{"type":25,"tag":129,"props":1108,"children":1109},{"style":142},[1110],{"type":34,"value":1111},"from",{"type":25,"tag":129,"props":1113,"children":1114},{"style":136},[1115],{"type":34,"value":1116}," sqlalchemy ",{"type":25,"tag":129,"props":1118,"children":1119},{"style":142},[1120],{"type":34,"value":286},{"type":25,"tag":129,"props":1122,"children":1123},{"style":136},[1124],{"type":34,"value":1125}," create_engine\n",{"type":25,"tag":129,"props":1127,"children":1128},{"class":131,"line":175},[1129,1133,1138,1142],{"type":25,"tag":129,"props":1130,"children":1131},{"style":142},[1132],{"type":34,"value":1111},{"type":25,"tag":129,"props":1134,"children":1135},{"style":136},[1136],{"type":34,"value":1137}," sqlalchemy.orm ",{"type":25,"tag":129,"props":1139,"children":1140},{"style":142},[1141],{"type":34,"value":286},{"type":25,"tag":129,"props":1143,"children":1144},{"style":136},[1145],{"type":34,"value":1146}," sessionmaker\n",{"type":25,"tag":129,"props":1148,"children":1149},{"class":131,"line":204},[1150,1154],{"type":25,"tag":129,"props":1151,"children":1152},{"style":142},[1153],{"type":34,"value":286},{"type":25,"tag":129,"props":1155,"children":1156},{"style":136},[1157],{"type":34,"value":1158}," os\n",{"type":25,"tag":129,"props":1160,"children":1161},{"class":131,"line":230},[1162,1166,1171,1175],{"type":25,"tag":129,"props":1163,"children":1164},{"style":142},[1165],{"type":34,"value":1111},{"type":25,"tag":129,"props":1167,"children":1168},{"style":136},[1169],{"type":34,"value":1170}," dotenv ",{"type":25,"tag":129,"props":1172,"children":1173},{"style":142},[1174],{"type":34,"value":286},{"type":25,"tag":129,"props":1176,"children":1177},{"style":136},[1178],{"type":34,"value":1179}," load_dotenv\n",{"type":25,"tag":129,"props":1181,"children":1182},{"class":131,"line":363},[1183],{"type":25,"tag":129,"props":1184,"children":1185},{"emptyLinePlaceholder":297},[1186],{"type":34,"value":300},{"type":25,"tag":129,"props":1188,"children":1189},{"class":131,"line":373},[1190],{"type":25,"tag":129,"props":1191,"children":1192},{"style":136},[1193],{"type":34,"value":1194},"load_dotenv()\n",{"type":25,"tag":129,"props":1196,"children":1198},{"class":131,"line":1197},7,[1199],{"type":25,"tag":129,"props":1200,"children":1201},{"emptyLinePlaceholder":297},[1202],{"type":34,"value":300},{"type":25,"tag":129,"props":1204,"children":1206},{"class":131,"line":1205},8,[1207,1212,1217,1222,1227],{"type":25,"tag":129,"props":1208,"children":1209},{"style":193},[1210],{"type":34,"value":1211},"DATABASE_URL",{"type":25,"tag":129,"props":1213,"children":1214},{"style":142},[1215],{"type":34,"value":1216}," =",{"type":25,"tag":129,"props":1218,"children":1219},{"style":136},[1220],{"type":34,"value":1221}," os.getenv(",{"type":25,"tag":129,"props":1223,"children":1224},{"style":164},[1225],{"type":34,"value":1226},"\"DATABASE_URL\"",{"type":25,"tag":129,"props":1228,"children":1229},{"style":136},[1230],{"type":34,"value":1231},")\n",{"type":25,"tag":129,"props":1233,"children":1235},{"class":131,"line":1234},9,[1236,1241,1245,1250,1254],{"type":25,"tag":129,"props":1237,"children":1238},{"style":136},[1239],{"type":34,"value":1240},"engine ",{"type":25,"tag":129,"props":1242,"children":1243},{"style":142},[1244],{"type":34,"value":145},{"type":25,"tag":129,"props":1246,"children":1247},{"style":136},[1248],{"type":34,"value":1249}," create_engine(",{"type":25,"tag":129,"props":1251,"children":1252},{"style":193},[1253],{"type":34,"value":1211},{"type":25,"tag":129,"props":1255,"children":1256},{"style":136},[1257],{"type":34,"value":1231},{"type":25,"tag":129,"props":1259,"children":1261},{"class":131,"line":1260},10,[1262,1267,1271,1276,1282,1286],{"type":25,"tag":129,"props":1263,"children":1264},{"style":136},[1265],{"type":34,"value":1266},"Session ",{"type":25,"tag":129,"props":1268,"children":1269},{"style":142},[1270],{"type":34,"value":145},{"type":25,"tag":129,"props":1272,"children":1273},{"style":136},[1274],{"type":34,"value":1275}," sessionmaker(",{"type":25,"tag":129,"props":1277,"children":1279},{"style":1278},"--shiki-default:#FFAB70;--shiki-light:#E36209",[1280],{"type":34,"value":1281},"bind",{"type":25,"tag":129,"props":1283,"children":1284},{"style":142},[1285],{"type":34,"value":145},{"type":25,"tag":129,"props":1287,"children":1288},{"style":136},[1289],{"type":34,"value":1290},"engine)\n",{"type":25,"tag":129,"props":1292,"children":1294},{"class":131,"line":1293},11,[1295,1300,1304],{"type":25,"tag":129,"props":1296,"children":1297},{"style":136},[1298],{"type":34,"value":1299},"session ",{"type":25,"tag":129,"props":1301,"children":1302},{"style":142},[1303],{"type":34,"value":145},{"type":25,"tag":129,"props":1305,"children":1306},{"style":136},[1307],{"type":34,"value":1308}," Session()\n",{"type":25,"tag":37,"props":1310,"children":1312},{"id":1311},"paso-3-obtener-esquema-de-la-base-de-datos",[1313],{"type":34,"value":1314},"Paso 3: Obtener esquema de la base de datos",{"type":25,"tag":30,"props":1316,"children":1317},{},[1318],{"type":34,"value":1319},"Genera una descripción del esquema que será utilizada por GPT:",{"type":25,"tag":120,"props":1321,"children":1323},{"className":1097,"code":1322,"language":1099,"meta":7,"style":7},"from sqlalchemy import inspect\n\ndef get_database_schema(engine):\n    inspector = inspect(engine)\n    schema_description = \"\"\n    for table_name in inspector.get_table_names():\n        schema_description += f\"Table: {table_name}\\n\"\n        for column in inspector.get_columns(table_name):\n            schema_description += f\"- {column['name']} ({column['type']})\\n\"\n        schema_description += \"\\n\"\n    return schema_description\n\nschema_description = get_database_schema(engine)\nprint(schema_description)\n",[1324],{"type":25,"tag":14,"props":1325,"children":1326},{"__ignoreMap":7},[1327,1347,1354,1372,1389,1406,1429,1472,1494,1579,1603,1616,1624,1642],{"type":25,"tag":129,"props":1328,"children":1329},{"class":131,"line":132},[1330,1334,1338,1342],{"type":25,"tag":129,"props":1331,"children":1332},{"style":142},[1333],{"type":34,"value":1111},{"type":25,"tag":129,"props":1335,"children":1336},{"style":136},[1337],{"type":34,"value":1116},{"type":25,"tag":129,"props":1339,"children":1340},{"style":142},[1341],{"type":34,"value":286},{"type":25,"tag":129,"props":1343,"children":1344},{"style":136},[1345],{"type":34,"value":1346}," inspect\n",{"type":25,"tag":129,"props":1348,"children":1349},{"class":131,"line":175},[1350],{"type":25,"tag":129,"props":1351,"children":1352},{"emptyLinePlaceholder":297},[1353],{"type":34,"value":300},{"type":25,"tag":129,"props":1355,"children":1356},{"class":131,"line":204},[1357,1362,1367],{"type":25,"tag":129,"props":1358,"children":1359},{"style":142},[1360],{"type":34,"value":1361},"def",{"type":25,"tag":129,"props":1363,"children":1364},{"style":153},[1365],{"type":34,"value":1366}," get_database_schema",{"type":25,"tag":129,"props":1368,"children":1369},{"style":136},[1370],{"type":34,"value":1371},"(engine):\n",{"type":25,"tag":129,"props":1373,"children":1374},{"class":131,"line":230},[1375,1380,1384],{"type":25,"tag":129,"props":1376,"children":1377},{"style":136},[1378],{"type":34,"value":1379},"    inspector ",{"type":25,"tag":129,"props":1381,"children":1382},{"style":142},[1383],{"type":34,"value":145},{"type":25,"tag":129,"props":1385,"children":1386},{"style":136},[1387],{"type":34,"value":1388}," inspect(engine)\n",{"type":25,"tag":129,"props":1390,"children":1391},{"class":131,"line":363},[1392,1397,1401],{"type":25,"tag":129,"props":1393,"children":1394},{"style":136},[1395],{"type":34,"value":1396},"    schema_description ",{"type":25,"tag":129,"props":1398,"children":1399},{"style":142},[1400],{"type":34,"value":145},{"type":25,"tag":129,"props":1402,"children":1403},{"style":164},[1404],{"type":34,"value":1405}," \"\"\n",{"type":25,"tag":129,"props":1407,"children":1408},{"class":131,"line":373},[1409,1414,1419,1424],{"type":25,"tag":129,"props":1410,"children":1411},{"style":142},[1412],{"type":34,"value":1413},"    for",{"type":25,"tag":129,"props":1415,"children":1416},{"style":136},[1417],{"type":34,"value":1418}," table_name ",{"type":25,"tag":129,"props":1420,"children":1421},{"style":142},[1422],{"type":34,"value":1423},"in",{"type":25,"tag":129,"props":1425,"children":1426},{"style":136},[1427],{"type":34,"value":1428}," inspector.get_table_names():\n",{"type":25,"tag":129,"props":1430,"children":1431},{"class":131,"line":1197},[1432,1437,1442,1447,1452,1457,1462,1467],{"type":25,"tag":129,"props":1433,"children":1434},{"style":136},[1435],{"type":34,"value":1436},"        schema_description ",{"type":25,"tag":129,"props":1438,"children":1439},{"style":142},[1440],{"type":34,"value":1441},"+=",{"type":25,"tag":129,"props":1443,"children":1444},{"style":142},[1445],{"type":34,"value":1446}," f",{"type":25,"tag":129,"props":1448,"children":1449},{"style":164},[1450],{"type":34,"value":1451},"\"Table: ",{"type":25,"tag":129,"props":1453,"children":1454},{"style":193},[1455],{"type":34,"value":1456},"{",{"type":25,"tag":129,"props":1458,"children":1459},{"style":136},[1460],{"type":34,"value":1461},"table_name",{"type":25,"tag":129,"props":1463,"children":1464},{"style":193},[1465],{"type":34,"value":1466},"}\\n",{"type":25,"tag":129,"props":1468,"children":1469},{"style":164},[1470],{"type":34,"value":1471},"\"\n",{"type":25,"tag":129,"props":1473,"children":1474},{"class":131,"line":1205},[1475,1480,1485,1489],{"type":25,"tag":129,"props":1476,"children":1477},{"style":142},[1478],{"type":34,"value":1479},"        for",{"type":25,"tag":129,"props":1481,"children":1482},{"style":136},[1483],{"type":34,"value":1484}," column ",{"type":25,"tag":129,"props":1486,"children":1487},{"style":142},[1488],{"type":34,"value":1423},{"type":25,"tag":129,"props":1490,"children":1491},{"style":136},[1492],{"type":34,"value":1493}," inspector.get_columns(table_name):\n",{"type":25,"tag":129,"props":1495,"children":1496},{"class":131,"line":1234},[1497,1502,1506,1510,1515,1519,1524,1529,1534,1539,1544,1548,1552,1557,1561,1565,1570,1575],{"type":25,"tag":129,"props":1498,"children":1499},{"style":136},[1500],{"type":34,"value":1501},"            schema_description ",{"type":25,"tag":129,"props":1503,"children":1504},{"style":142},[1505],{"type":34,"value":1441},{"type":25,"tag":129,"props":1507,"children":1508},{"style":142},[1509],{"type":34,"value":1446},{"type":25,"tag":129,"props":1511,"children":1512},{"style":164},[1513],{"type":34,"value":1514},"\"- ",{"type":25,"tag":129,"props":1516,"children":1517},{"style":193},[1518],{"type":34,"value":1456},{"type":25,"tag":129,"props":1520,"children":1521},{"style":136},[1522],{"type":34,"value":1523},"column[",{"type":25,"tag":129,"props":1525,"children":1526},{"style":164},[1527],{"type":34,"value":1528},"'name'",{"type":25,"tag":129,"props":1530,"children":1531},{"style":136},[1532],{"type":34,"value":1533},"]",{"type":25,"tag":129,"props":1535,"children":1536},{"style":193},[1537],{"type":34,"value":1538},"}",{"type":25,"tag":129,"props":1540,"children":1541},{"style":164},[1542],{"type":34,"value":1543}," (",{"type":25,"tag":129,"props":1545,"children":1546},{"style":193},[1547],{"type":34,"value":1456},{"type":25,"tag":129,"props":1549,"children":1550},{"style":136},[1551],{"type":34,"value":1523},{"type":25,"tag":129,"props":1553,"children":1554},{"style":164},[1555],{"type":34,"value":1556},"'type'",{"type":25,"tag":129,"props":1558,"children":1559},{"style":136},[1560],{"type":34,"value":1533},{"type":25,"tag":129,"props":1562,"children":1563},{"style":193},[1564],{"type":34,"value":1538},{"type":25,"tag":129,"props":1566,"children":1567},{"style":164},[1568],{"type":34,"value":1569},")",{"type":25,"tag":129,"props":1571,"children":1572},{"style":193},[1573],{"type":34,"value":1574},"\\n",{"type":25,"tag":129,"props":1576,"children":1577},{"style":164},[1578],{"type":34,"value":1471},{"type":25,"tag":129,"props":1580,"children":1581},{"class":131,"line":1260},[1582,1586,1590,1595,1599],{"type":25,"tag":129,"props":1583,"children":1584},{"style":136},[1585],{"type":34,"value":1436},{"type":25,"tag":129,"props":1587,"children":1588},{"style":142},[1589],{"type":34,"value":1441},{"type":25,"tag":129,"props":1591,"children":1592},{"style":164},[1593],{"type":34,"value":1594}," \"",{"type":25,"tag":129,"props":1596,"children":1597},{"style":193},[1598],{"type":34,"value":1574},{"type":25,"tag":129,"props":1600,"children":1601},{"style":164},[1602],{"type":34,"value":1471},{"type":25,"tag":129,"props":1604,"children":1605},{"class":131,"line":1293},[1606,1611],{"type":25,"tag":129,"props":1607,"children":1608},{"style":142},[1609],{"type":34,"value":1610},"    return",{"type":25,"tag":129,"props":1612,"children":1613},{"style":136},[1614],{"type":34,"value":1615}," schema_description\n",{"type":25,"tag":129,"props":1617,"children":1619},{"class":131,"line":1618},12,[1620],{"type":25,"tag":129,"props":1621,"children":1622},{"emptyLinePlaceholder":297},[1623],{"type":34,"value":300},{"type":25,"tag":129,"props":1625,"children":1627},{"class":131,"line":1626},13,[1628,1633,1637],{"type":25,"tag":129,"props":1629,"children":1630},{"style":136},[1631],{"type":34,"value":1632},"schema_description ",{"type":25,"tag":129,"props":1634,"children":1635},{"style":142},[1636],{"type":34,"value":145},{"type":25,"tag":129,"props":1638,"children":1639},{"style":136},[1640],{"type":34,"value":1641}," get_database_schema(engine)\n",{"type":25,"tag":129,"props":1643,"children":1645},{"class":131,"line":1644},14,[1646,1651],{"type":25,"tag":129,"props":1647,"children":1648},{"style":193},[1649],{"type":34,"value":1650},"print",{"type":25,"tag":129,"props":1652,"children":1653},{"style":136},[1654],{"type":34,"value":1655},"(schema_description)\n",{"type":25,"tag":37,"props":1657,"children":1659},{"id":1658},"paso-4-preparar-la-consulta-con-gpt",[1660],{"type":34,"value":1661},"Paso 4: Preparar la consulta con GPT",{"type":25,"tag":30,"props":1663,"children":1664},{},[1665],{"type":34,"value":1666},"Utiliza la API de OpenAI para transformar preguntas en consultas SQL, incluyendo el esquema de la base de datos:",{"type":25,"tag":120,"props":1668,"children":1670},{"className":1097,"code":1669,"language":1099,"meta":7,"style":7},"import openai\nimport os\n\nopenai.api_key = os.getenv(\"OPENAI_API_KEY\")\n\ndef generate_sql(question, schema):\n    response = openai.ChatCompletion.create(\n        model=\"gpt-4\",\n        messages=[\n            {\"role\": \"system\", \"content\": f\"Convierte preguntas en lenguaje natural a consultas SQL. Esquema de la base de datos:\\n{schema}\"},\n            {\"role\": \"user\", \"content\": question}\n        ]\n    )\n    sql_query = response.choices[0].message.content.strip()\n    return sql_query\n\nquery = generate_sql(\"¿Cuántos usuarios se registraron el último mes?\", schema_description)\nprint(query)\n",[1671],{"type":25,"tag":14,"props":1672,"children":1673},{"__ignoreMap":7},[1674,1686,1697,1704,1729,1736,1753,1770,1792,1809,1880,1913,1921,1929,1956,1969,1977,2005],{"type":25,"tag":129,"props":1675,"children":1676},{"class":131,"line":132},[1677,1681],{"type":25,"tag":129,"props":1678,"children":1679},{"style":142},[1680],{"type":34,"value":286},{"type":25,"tag":129,"props":1682,"children":1683},{"style":136},[1684],{"type":34,"value":1685}," openai\n",{"type":25,"tag":129,"props":1687,"children":1688},{"class":131,"line":175},[1689,1693],{"type":25,"tag":129,"props":1690,"children":1691},{"style":142},[1692],{"type":34,"value":286},{"type":25,"tag":129,"props":1694,"children":1695},{"style":136},[1696],{"type":34,"value":1158},{"type":25,"tag":129,"props":1698,"children":1699},{"class":131,"line":204},[1700],{"type":25,"tag":129,"props":1701,"children":1702},{"emptyLinePlaceholder":297},[1703],{"type":34,"value":300},{"type":25,"tag":129,"props":1705,"children":1706},{"class":131,"line":230},[1707,1712,1716,1720,1725],{"type":25,"tag":129,"props":1708,"children":1709},{"style":136},[1710],{"type":34,"value":1711},"openai.api_key ",{"type":25,"tag":129,"props":1713,"children":1714},{"style":142},[1715],{"type":34,"value":145},{"type":25,"tag":129,"props":1717,"children":1718},{"style":136},[1719],{"type":34,"value":1221},{"type":25,"tag":129,"props":1721,"children":1722},{"style":164},[1723],{"type":34,"value":1724},"\"OPENAI_API_KEY\"",{"type":25,"tag":129,"props":1726,"children":1727},{"style":136},[1728],{"type":34,"value":1231},{"type":25,"tag":129,"props":1730,"children":1731},{"class":131,"line":363},[1732],{"type":25,"tag":129,"props":1733,"children":1734},{"emptyLinePlaceholder":297},[1735],{"type":34,"value":300},{"type":25,"tag":129,"props":1737,"children":1738},{"class":131,"line":373},[1739,1743,1748],{"type":25,"tag":129,"props":1740,"children":1741},{"style":142},[1742],{"type":34,"value":1361},{"type":25,"tag":129,"props":1744,"children":1745},{"style":153},[1746],{"type":34,"value":1747}," generate_sql",{"type":25,"tag":129,"props":1749,"children":1750},{"style":136},[1751],{"type":34,"value":1752},"(question, schema):\n",{"type":25,"tag":129,"props":1754,"children":1755},{"class":131,"line":1197},[1756,1761,1765],{"type":25,"tag":129,"props":1757,"children":1758},{"style":136},[1759],{"type":34,"value":1760},"    response ",{"type":25,"tag":129,"props":1762,"children":1763},{"style":142},[1764],{"type":34,"value":145},{"type":25,"tag":129,"props":1766,"children":1767},{"style":136},[1768],{"type":34,"value":1769}," openai.ChatCompletion.create(\n",{"type":25,"tag":129,"props":1771,"children":1772},{"class":131,"line":1205},[1773,1778,1782,1787],{"type":25,"tag":129,"props":1774,"children":1775},{"style":1278},[1776],{"type":34,"value":1777},"        model",{"type":25,"tag":129,"props":1779,"children":1780},{"style":142},[1781],{"type":34,"value":145},{"type":25,"tag":129,"props":1783,"children":1784},{"style":164},[1785],{"type":34,"value":1786},"\"gpt-4\"",{"type":25,"tag":129,"props":1788,"children":1789},{"style":136},[1790],{"type":34,"value":1791},",\n",{"type":25,"tag":129,"props":1793,"children":1794},{"class":131,"line":1234},[1795,1800,1804],{"type":25,"tag":129,"props":1796,"children":1797},{"style":1278},[1798],{"type":34,"value":1799},"        messages",{"type":25,"tag":129,"props":1801,"children":1802},{"style":142},[1803],{"type":34,"value":145},{"type":25,"tag":129,"props":1805,"children":1806},{"style":136},[1807],{"type":34,"value":1808},"[\n",{"type":25,"tag":129,"props":1810,"children":1811},{"class":131,"line":1260},[1812,1817,1822,1827,1832,1837,1842,1846,1851,1856,1861,1866,1870,1875],{"type":25,"tag":129,"props":1813,"children":1814},{"style":136},[1815],{"type":34,"value":1816},"            {",{"type":25,"tag":129,"props":1818,"children":1819},{"style":164},[1820],{"type":34,"value":1821},"\"role\"",{"type":25,"tag":129,"props":1823,"children":1824},{"style":136},[1825],{"type":34,"value":1826},": ",{"type":25,"tag":129,"props":1828,"children":1829},{"style":164},[1830],{"type":34,"value":1831},"\"system\"",{"type":25,"tag":129,"props":1833,"children":1834},{"style":136},[1835],{"type":34,"value":1836},", ",{"type":25,"tag":129,"props":1838,"children":1839},{"style":164},[1840],{"type":34,"value":1841},"\"content\"",{"type":25,"tag":129,"props":1843,"children":1844},{"style":136},[1845],{"type":34,"value":1826},{"type":25,"tag":129,"props":1847,"children":1848},{"style":142},[1849],{"type":34,"value":1850},"f",{"type":25,"tag":129,"props":1852,"children":1853},{"style":164},[1854],{"type":34,"value":1855},"\"Convierte preguntas en lenguaje natural a consultas SQL. Esquema de la base de datos:",{"type":25,"tag":129,"props":1857,"children":1858},{"style":193},[1859],{"type":34,"value":1860},"\\n{",{"type":25,"tag":129,"props":1862,"children":1863},{"style":136},[1864],{"type":34,"value":1865},"schema",{"type":25,"tag":129,"props":1867,"children":1868},{"style":193},[1869],{"type":34,"value":1538},{"type":25,"tag":129,"props":1871,"children":1872},{"style":164},[1873],{"type":34,"value":1874},"\"",{"type":25,"tag":129,"props":1876,"children":1877},{"style":136},[1878],{"type":34,"value":1879},"},\n",{"type":25,"tag":129,"props":1881,"children":1882},{"class":131,"line":1293},[1883,1887,1891,1895,1900,1904,1908],{"type":25,"tag":129,"props":1884,"children":1885},{"style":136},[1886],{"type":34,"value":1816},{"type":25,"tag":129,"props":1888,"children":1889},{"style":164},[1890],{"type":34,"value":1821},{"type":25,"tag":129,"props":1892,"children":1893},{"style":136},[1894],{"type":34,"value":1826},{"type":25,"tag":129,"props":1896,"children":1897},{"style":164},[1898],{"type":34,"value":1899},"\"user\"",{"type":25,"tag":129,"props":1901,"children":1902},{"style":136},[1903],{"type":34,"value":1836},{"type":25,"tag":129,"props":1905,"children":1906},{"style":164},[1907],{"type":34,"value":1841},{"type":25,"tag":129,"props":1909,"children":1910},{"style":136},[1911],{"type":34,"value":1912},": question}\n",{"type":25,"tag":129,"props":1914,"children":1915},{"class":131,"line":1618},[1916],{"type":25,"tag":129,"props":1917,"children":1918},{"style":136},[1919],{"type":34,"value":1920},"        ]\n",{"type":25,"tag":129,"props":1922,"children":1923},{"class":131,"line":1626},[1924],{"type":25,"tag":129,"props":1925,"children":1926},{"style":136},[1927],{"type":34,"value":1928},"    )\n",{"type":25,"tag":129,"props":1930,"children":1931},{"class":131,"line":1644},[1932,1937,1941,1946,1951],{"type":25,"tag":129,"props":1933,"children":1934},{"style":136},[1935],{"type":34,"value":1936},"    sql_query ",{"type":25,"tag":129,"props":1938,"children":1939},{"style":142},[1940],{"type":34,"value":145},{"type":25,"tag":129,"props":1942,"children":1943},{"style":136},[1944],{"type":34,"value":1945}," response.choices[",{"type":25,"tag":129,"props":1947,"children":1948},{"style":193},[1949],{"type":34,"value":1950},"0",{"type":25,"tag":129,"props":1952,"children":1953},{"style":136},[1954],{"type":34,"value":1955},"].message.content.strip()\n",{"type":25,"tag":129,"props":1957,"children":1959},{"class":131,"line":1958},15,[1960,1964],{"type":25,"tag":129,"props":1961,"children":1962},{"style":142},[1963],{"type":34,"value":1610},{"type":25,"tag":129,"props":1965,"children":1966},{"style":136},[1967],{"type":34,"value":1968}," sql_query\n",{"type":25,"tag":129,"props":1970,"children":1972},{"class":131,"line":1971},16,[1973],{"type":25,"tag":129,"props":1974,"children":1975},{"emptyLinePlaceholder":297},[1976],{"type":34,"value":300},{"type":25,"tag":129,"props":1978,"children":1980},{"class":131,"line":1979},17,[1981,1986,1990,1995,2000],{"type":25,"tag":129,"props":1982,"children":1983},{"style":136},[1984],{"type":34,"value":1985},"query ",{"type":25,"tag":129,"props":1987,"children":1988},{"style":142},[1989],{"type":34,"value":145},{"type":25,"tag":129,"props":1991,"children":1992},{"style":136},[1993],{"type":34,"value":1994}," generate_sql(",{"type":25,"tag":129,"props":1996,"children":1997},{"style":164},[1998],{"type":34,"value":1999},"\"¿Cuántos usuarios se registraron el último mes?\"",{"type":25,"tag":129,"props":2001,"children":2002},{"style":136},[2003],{"type":34,"value":2004},", schema_description)\n",{"type":25,"tag":129,"props":2006,"children":2008},{"class":131,"line":2007},18,[2009,2013],{"type":25,"tag":129,"props":2010,"children":2011},{"style":193},[2012],{"type":34,"value":1650},{"type":25,"tag":129,"props":2014,"children":2015},{"style":136},[2016],{"type":34,"value":2017},"(query)\n",{"type":25,"tag":37,"props":2019,"children":2021},{"id":2020},"paso-5-ejecutar-consultas-generadas",[2022],{"type":34,"value":2023},"Paso 5: Ejecutar consultas generadas",{"type":25,"tag":30,"props":2025,"children":2026},{},[2027],{"type":34,"value":2028},"Ejecuta la consulta generada y obtiene resultados:",{"type":25,"tag":120,"props":2030,"children":2032},{"className":1097,"code":2031,"language":1099,"meta":7,"style":7},"result = session.execute(query)\nfor row in result:\n    print(row)\n",[2033],{"type":25,"tag":14,"props":2034,"children":2035},{"__ignoreMap":7},[2036,2053,2075],{"type":25,"tag":129,"props":2037,"children":2038},{"class":131,"line":132},[2039,2044,2048],{"type":25,"tag":129,"props":2040,"children":2041},{"style":136},[2042],{"type":34,"value":2043},"result ",{"type":25,"tag":129,"props":2045,"children":2046},{"style":142},[2047],{"type":34,"value":145},{"type":25,"tag":129,"props":2049,"children":2050},{"style":136},[2051],{"type":34,"value":2052}," session.execute(query)\n",{"type":25,"tag":129,"props":2054,"children":2055},{"class":131,"line":175},[2056,2061,2066,2070],{"type":25,"tag":129,"props":2057,"children":2058},{"style":142},[2059],{"type":34,"value":2060},"for",{"type":25,"tag":129,"props":2062,"children":2063},{"style":136},[2064],{"type":34,"value":2065}," row ",{"type":25,"tag":129,"props":2067,"children":2068},{"style":142},[2069],{"type":34,"value":1423},{"type":25,"tag":129,"props":2071,"children":2072},{"style":136},[2073],{"type":34,"value":2074}," result:\n",{"type":25,"tag":129,"props":2076,"children":2077},{"class":131,"line":204},[2078,2083],{"type":25,"tag":129,"props":2079,"children":2080},{"style":193},[2081],{"type":34,"value":2082},"    print",{"type":25,"tag":129,"props":2084,"children":2085},{"style":136},[2086],{"type":34,"value":2087},"(row)\n",{"type":25,"tag":37,"props":2089,"children":2091},{"id":2090},"paso-6-manejo-de-errores-y-seguridad",[2092],{"type":34,"value":2093},"Paso 6: Manejo de errores y seguridad",{"type":25,"tag":30,"props":2095,"children":2096},{},[2097],{"type":34,"value":2098},"Para evitar problemas con consultas inseguras o errores, siempre valida las consultas generadas por GPT antes de ejecutarlas directamente:",{"type":25,"tag":120,"props":2100,"children":2102},{"className":1097,"code":2101,"language":1099,"meta":7,"style":7},"def execute_safe_query(sql_query):\n    try:\n        result = session.execute(sql_query)\n        return result.fetchall()\n    except Exception as e:\n        print(f\"Error al ejecutar consulta: {e}\")\n        return None\n\nresults = execute_safe_query(query)\nprint(results)\n",[2103],{"type":25,"tag":14,"props":2104,"children":2105},{"__ignoreMap":7},[2106,2123,2136,2153,2166,2189,2231,2243,2250,2267],{"type":25,"tag":129,"props":2107,"children":2108},{"class":131,"line":132},[2109,2113,2118],{"type":25,"tag":129,"props":2110,"children":2111},{"style":142},[2112],{"type":34,"value":1361},{"type":25,"tag":129,"props":2114,"children":2115},{"style":153},[2116],{"type":34,"value":2117}," execute_safe_query",{"type":25,"tag":129,"props":2119,"children":2120},{"style":136},[2121],{"type":34,"value":2122},"(sql_query):\n",{"type":25,"tag":129,"props":2124,"children":2125},{"class":131,"line":175},[2126,2131],{"type":25,"tag":129,"props":2127,"children":2128},{"style":142},[2129],{"type":34,"value":2130},"    try",{"type":25,"tag":129,"props":2132,"children":2133},{"style":136},[2134],{"type":34,"value":2135},":\n",{"type":25,"tag":129,"props":2137,"children":2138},{"class":131,"line":204},[2139,2144,2148],{"type":25,"tag":129,"props":2140,"children":2141},{"style":136},[2142],{"type":34,"value":2143},"        result ",{"type":25,"tag":129,"props":2145,"children":2146},{"style":142},[2147],{"type":34,"value":145},{"type":25,"tag":129,"props":2149,"children":2150},{"style":136},[2151],{"type":34,"value":2152}," session.execute(sql_query)\n",{"type":25,"tag":129,"props":2154,"children":2155},{"class":131,"line":230},[2156,2161],{"type":25,"tag":129,"props":2157,"children":2158},{"style":142},[2159],{"type":34,"value":2160},"        return",{"type":25,"tag":129,"props":2162,"children":2163},{"style":136},[2164],{"type":34,"value":2165}," result.fetchall()\n",{"type":25,"tag":129,"props":2167,"children":2168},{"class":131,"line":363},[2169,2174,2179,2184],{"type":25,"tag":129,"props":2170,"children":2171},{"style":142},[2172],{"type":34,"value":2173},"    except",{"type":25,"tag":129,"props":2175,"children":2176},{"style":193},[2177],{"type":34,"value":2178}," Exception",{"type":25,"tag":129,"props":2180,"children":2181},{"style":142},[2182],{"type":34,"value":2183}," as",{"type":25,"tag":129,"props":2185,"children":2186},{"style":136},[2187],{"type":34,"value":2188}," e:\n",{"type":25,"tag":129,"props":2190,"children":2191},{"class":131,"line":373},[2192,2197,2201,2205,2210,2214,2219,2223,2227],{"type":25,"tag":129,"props":2193,"children":2194},{"style":193},[2195],{"type":34,"value":2196},"        print",{"type":25,"tag":129,"props":2198,"children":2199},{"style":136},[2200],{"type":34,"value":161},{"type":25,"tag":129,"props":2202,"children":2203},{"style":142},[2204],{"type":34,"value":1850},{"type":25,"tag":129,"props":2206,"children":2207},{"style":164},[2208],{"type":34,"value":2209},"\"Error al ejecutar consulta: ",{"type":25,"tag":129,"props":2211,"children":2212},{"style":193},[2213],{"type":34,"value":1456},{"type":25,"tag":129,"props":2215,"children":2216},{"style":136},[2217],{"type":34,"value":2218},"e",{"type":25,"tag":129,"props":2220,"children":2221},{"style":193},[2222],{"type":34,"value":1538},{"type":25,"tag":129,"props":2224,"children":2225},{"style":164},[2226],{"type":34,"value":1874},{"type":25,"tag":129,"props":2228,"children":2229},{"style":136},[2230],{"type":34,"value":1231},{"type":25,"tag":129,"props":2232,"children":2233},{"class":131,"line":1197},[2234,2238],{"type":25,"tag":129,"props":2235,"children":2236},{"style":142},[2237],{"type":34,"value":2160},{"type":25,"tag":129,"props":2239,"children":2240},{"style":193},[2241],{"type":34,"value":2242}," None\n",{"type":25,"tag":129,"props":2244,"children":2245},{"class":131,"line":1205},[2246],{"type":25,"tag":129,"props":2247,"children":2248},{"emptyLinePlaceholder":297},[2249],{"type":34,"value":300},{"type":25,"tag":129,"props":2251,"children":2252},{"class":131,"line":1234},[2253,2258,2262],{"type":25,"tag":129,"props":2254,"children":2255},{"style":136},[2256],{"type":34,"value":2257},"results ",{"type":25,"tag":129,"props":2259,"children":2260},{"style":142},[2261],{"type":34,"value":145},{"type":25,"tag":129,"props":2263,"children":2264},{"style":136},[2265],{"type":34,"value":2266}," execute_safe_query(query)\n",{"type":25,"tag":129,"props":2268,"children":2269},{"class":131,"line":1260},[2270,2274],{"type":25,"tag":129,"props":2271,"children":2272},{"style":193},[2273],{"type":34,"value":1650},{"type":25,"tag":129,"props":2275,"children":2276},{"style":136},[2277],{"type":34,"value":2278},"(results)\n",{"type":25,"tag":37,"props":2280,"children":2282},{"id":2281},"buenas-prácticas",[2283],{"type":34,"value":2284},"Buenas prácticas",{"type":25,"tag":895,"props":2286,"children":2287},{},[2288,2293,2298],{"type":25,"tag":53,"props":2289,"children":2290},{},[2291],{"type":34,"value":2292},"Siempre revisa o limita el acceso de los usuarios a consultas críticas o sensibles.",{"type":25,"tag":53,"props":2294,"children":2295},{},[2296],{"type":34,"value":2297},"Implementa validaciones adicionales para asegurar la integridad y seguridad de tu base de datos.",{"type":25,"tag":53,"props":2299,"children":2300},{},[2301],{"type":34,"value":2302},"Utiliza tokens y modelos específicos de OpenAI optimizados para tareas SQL.",{"type":25,"tag":37,"props":2304,"children":2306},{"id":2305},"conclusión",[2307],{"type":34,"value":2308},"Conclusión",{"type":25,"tag":30,"props":2310,"children":2311},{},[2312],{"type":34,"value":2313},"Utilizar GPT para transformar consultas en lenguaje natural a SQL facilita enormemente la accesibilidad a los datos. Implementando este sistema, podrás ofrecer una experiencia de usuario más amigable y eficiente.",{"type":25,"tag":888,"props":2315,"children":2317},{"id":2316},"recursos-adicionales",[2318],{"type":34,"value":2319},"Recursos adicionales",{"type":25,"tag":895,"props":2321,"children":2322},{},[2323,2333,2343],{"type":25,"tag":53,"props":2324,"children":2325},{},[2326],{"type":25,"tag":902,"props":2327,"children":2330},{"href":2328,"rel":2329},"https://platform.openai.com/docs/api-reference",[906],[2331],{"type":34,"value":2332},"Documentación API OpenAI",{"type":25,"tag":53,"props":2334,"children":2335},{},[2336],{"type":25,"tag":902,"props":2337,"children":2340},{"href":2338,"rel":2339},"https://docs.sqlalchemy.org/en/20/",[906],[2341],{"type":34,"value":2342},"SQLAlchemy ORM Documentation",{"type":25,"tag":53,"props":2344,"children":2345},{},[2346],{"type":25,"tag":902,"props":2347,"children":2350},{"href":2348,"rel":2349},"https://pypi.org/project/python-dotenv/",[906],[2351],{"type":34,"value":2352},"Python Dotenv",{"type":25,"tag":931,"props":2354,"children":2355},{},[2356],{"type":34,"value":935},{"title":7,"searchDepth":175,"depth":175,"links":2358},[2359,2360,2361,2362,2363,2364,2365,2366,2367],{"id":980,"depth":175,"text":983},{"id":1004,"depth":175,"text":1007},{"id":1086,"depth":175,"text":1089},{"id":1311,"depth":175,"text":1314},{"id":1658,"depth":175,"text":1661},{"id":2020,"depth":175,"text":2023},{"id":2090,"depth":175,"text":2093},{"id":2281,"depth":175,"text":2284},{"id":2305,"depth":175,"text":2308},"content:posts:gpt-sql-integration.md","posts/gpt-sql-integration.md","posts/gpt-sql-integration",{"_path":2372,"_dir":5,"_draft":6,"_partial":6,"_locale":7,"title":2373,"description":2374,"date":2375,"layout":11,"subtitle":2376,"image":2377,"optimized_image":2377,"category":14,"tags":2378,"author":20,"paginate":6,"body":2382,"_type":948,"_id":3188,"_source":950,"_file":3189,"_stem":3190,"_extension":953},"/posts/circuit-breaking-resilience","Circuit Breaking in Distributed Systems","An expert guide to understanding and implementing circuit breakers in distributed systems, with practical Java examples using Resilience4j and best practices.","2024-07-15T11:00:00.000Z","Enhancing Resilience with Circuit Breaker Patterns","/assets/img/uploads/circuit-breaking-resilience.png",[14,16,2379,2380,2381],"resilience","circuit-breaker","distributed-systems",{"type":22,"children":2383,"toc":3176},[2384,2392,2398,2403,2437,2442,2448,2453,2471,2477,2484,2489,2599,2605,2809,2815,2820,2987,2993,2998,3092,3097,3103,3126,3130,3135,3139,3172],{"type":25,"tag":26,"props":2385,"children":2386},{},[2387],{"type":25,"tag":30,"props":2388,"children":2389},{},[2390],{"type":34,"value":2391},"In modern distributed systems, failures are inevitable. The circuit breaker pattern helps maintain system stability by preventing failures from cascading across service boundaries. In this post, we'll dive deep into circuit breakers, explore their importance, and demonstrate practical implementation using Resilience4j in Java.",{"type":25,"tag":37,"props":2393,"children":2395},{"id":2394},"understanding-the-circuit-breaker-pattern",[2396],{"type":34,"value":2397},"Understanding the Circuit Breaker Pattern",{"type":25,"tag":30,"props":2399,"children":2400},{},[2401],{"type":34,"value":2402},"The circuit breaker pattern prevents a service from making repeated calls to an external service that is experiencing issues. It has three main states:",{"type":25,"tag":895,"props":2404,"children":2405},{},[2406,2417,2427],{"type":25,"tag":53,"props":2407,"children":2408},{},[2409,2415],{"type":25,"tag":2410,"props":2411,"children":2412},"strong",{},[2413],{"type":34,"value":2414},"Closed:",{"type":34,"value":2416}," All requests pass through normally.",{"type":25,"tag":53,"props":2418,"children":2419},{},[2420,2425],{"type":25,"tag":2410,"props":2421,"children":2422},{},[2423],{"type":34,"value":2424},"Open:",{"type":34,"value":2426}," Requests fail fast, bypassing the problematic service.",{"type":25,"tag":53,"props":2428,"children":2429},{},[2430,2435],{"type":25,"tag":2410,"props":2431,"children":2432},{},[2433],{"type":34,"value":2434},"Half-Open:",{"type":34,"value":2436}," A limited number of requests test if the external service has recovered.",{"type":25,"tag":30,"props":2438,"children":2439},{},[2440],{"type":34,"value":2441},"This mechanism helps improve the resilience and responsiveness of your systems.",{"type":25,"tag":37,"props":2443,"children":2445},{"id":2444},"when-to-use-circuit-breakers",[2446],{"type":34,"value":2447},"When to Use Circuit Breakers",{"type":25,"tag":30,"props":2449,"children":2450},{},[2451],{"type":34,"value":2452},"Circuit breakers are essential when:",{"type":25,"tag":895,"props":2454,"children":2455},{},[2456,2461,2466],{"type":25,"tag":53,"props":2457,"children":2458},{},[2459],{"type":34,"value":2460},"Your system relies on remote calls (microservices architecture, external APIs).",{"type":25,"tag":53,"props":2462,"children":2463},{},[2464],{"type":34,"value":2465},"You need to prevent failure propagation.",{"type":25,"tag":53,"props":2467,"children":2468},{},[2469],{"type":34,"value":2470},"You aim to improve user experience by quickly responding to failures.",{"type":25,"tag":37,"props":2472,"children":2474},{"id":2473},"implementing-circuit-breakers-with-resilience4j",[2475],{"type":34,"value":2476},"Implementing Circuit Breakers with Resilience4j",{"type":25,"tag":2478,"props":2479,"children":2481},"h3",{"id":2480},"step-1-adding-dependencies",[2482],{"type":34,"value":2483},"Step 1: Adding Dependencies",{"type":25,"tag":30,"props":2485,"children":2486},{},[2487],{"type":34,"value":2488},"Add Resilience4j dependencies to your project (Maven example):",{"type":25,"tag":120,"props":2490,"children":2492},{"className":704,"code":2491,"language":706,"meta":7,"style":7},"\u003Cdependency>\n    \u003CgroupId>io.github.resilience4j\u003C/groupId>\n    \u003CartifactId>resilience4j-circuitbreaker\u003C/artifactId>\n    \u003Cversion>2.0.2\u003C/version>\n\u003C/dependency>\n",[2493],{"type":25,"tag":14,"props":2494,"children":2495},{"__ignoreMap":7},[2496,2512,2536,2560,2584],{"type":25,"tag":129,"props":2497,"children":2498},{"class":131,"line":132},[2499,2503,2508],{"type":25,"tag":129,"props":2500,"children":2501},{"style":136},[2502],{"type":34,"value":718},{"type":25,"tag":129,"props":2504,"children":2505},{"style":721},[2506],{"type":34,"value":2507},"dependency",{"type":25,"tag":129,"props":2509,"children":2510},{"style":136},[2511],{"type":34,"value":729},{"type":25,"tag":129,"props":2513,"children":2514},{"class":131,"line":175},[2515,2519,2523,2528,2532],{"type":25,"tag":129,"props":2516,"children":2517},{"style":136},[2518],{"type":34,"value":737},{"type":25,"tag":129,"props":2520,"children":2521},{"style":721},[2522],{"type":34,"value":742},{"type":25,"tag":129,"props":2524,"children":2525},{"style":136},[2526],{"type":34,"value":2527},">io.github.resilience4j\u003C/",{"type":25,"tag":129,"props":2529,"children":2530},{"style":721},[2531],{"type":34,"value":742},{"type":25,"tag":129,"props":2533,"children":2534},{"style":136},[2535],{"type":34,"value":729},{"type":25,"tag":129,"props":2537,"children":2538},{"class":131,"line":204},[2539,2543,2547,2552,2556],{"type":25,"tag":129,"props":2540,"children":2541},{"style":136},[2542],{"type":34,"value":737},{"type":25,"tag":129,"props":2544,"children":2545},{"style":721},[2546],{"type":34,"value":767},{"type":25,"tag":129,"props":2548,"children":2549},{"style":136},[2550],{"type":34,"value":2551},">resilience4j-circuitbreaker\u003C/",{"type":25,"tag":129,"props":2553,"children":2554},{"style":721},[2555],{"type":34,"value":767},{"type":25,"tag":129,"props":2557,"children":2558},{"style":136},[2559],{"type":34,"value":729},{"type":25,"tag":129,"props":2561,"children":2562},{"class":131,"line":230},[2563,2567,2571,2576,2580],{"type":25,"tag":129,"props":2564,"children":2565},{"style":136},[2566],{"type":34,"value":737},{"type":25,"tag":129,"props":2568,"children":2569},{"style":721},[2570],{"type":34,"value":792},{"type":25,"tag":129,"props":2572,"children":2573},{"style":136},[2574],{"type":34,"value":2575},">2.0.2\u003C/",{"type":25,"tag":129,"props":2577,"children":2578},{"style":721},[2579],{"type":34,"value":792},{"type":25,"tag":129,"props":2581,"children":2582},{"style":136},[2583],{"type":34,"value":729},{"type":25,"tag":129,"props":2585,"children":2586},{"class":131,"line":363},[2587,2591,2595],{"type":25,"tag":129,"props":2588,"children":2589},{"style":136},[2590],{"type":34,"value":813},{"type":25,"tag":129,"props":2592,"children":2593},{"style":721},[2594],{"type":34,"value":2507},{"type":25,"tag":129,"props":2596,"children":2597},{"style":136},[2598],{"type":34,"value":729},{"type":25,"tag":2478,"props":2600,"children":2602},{"id":2601},"step-2-configuring-circuit-breaker",[2603],{"type":34,"value":2604},"Step 2: Configuring Circuit Breaker",{"type":25,"tag":120,"props":2606,"children":2608},{"className":122,"code":2607,"language":16,"meta":7,"style":7},"CircuitBreakerConfig config = CircuitBreakerConfig.custom()\n    .failureRateThreshold(50)\n    .waitDurationInOpenState(Duration.ofMillis(1000))\n    .permittedNumberOfCallsInHalfOpenState(2)\n    .minimumNumberOfCalls(5)\n    .build();\n\nCircuitBreaker circuitBreaker = CircuitBreaker.of(\"myService\", config);\n",[2609],{"type":25,"tag":14,"props":2610,"children":2611},{"__ignoreMap":7},[2612,2639,2665,2701,2725,2750,2766,2773],{"type":25,"tag":129,"props":2613,"children":2614},{"class":131,"line":132},[2615,2620,2624,2629,2634],{"type":25,"tag":129,"props":2616,"children":2617},{"style":136},[2618],{"type":34,"value":2619},"CircuitBreakerConfig config ",{"type":25,"tag":129,"props":2621,"children":2622},{"style":142},[2623],{"type":34,"value":145},{"type":25,"tag":129,"props":2625,"children":2626},{"style":136},[2627],{"type":34,"value":2628}," CircuitBreakerConfig.",{"type":25,"tag":129,"props":2630,"children":2631},{"style":153},[2632],{"type":34,"value":2633},"custom",{"type":25,"tag":129,"props":2635,"children":2636},{"style":136},[2637],{"type":34,"value":2638},"()\n",{"type":25,"tag":129,"props":2640,"children":2641},{"class":131,"line":175},[2642,2647,2652,2656,2661],{"type":25,"tag":129,"props":2643,"children":2644},{"style":136},[2645],{"type":34,"value":2646},"    .",{"type":25,"tag":129,"props":2648,"children":2649},{"style":153},[2650],{"type":34,"value":2651},"failureRateThreshold",{"type":25,"tag":129,"props":2653,"children":2654},{"style":136},[2655],{"type":34,"value":161},{"type":25,"tag":129,"props":2657,"children":2658},{"style":193},[2659],{"type":34,"value":2660},"50",{"type":25,"tag":129,"props":2662,"children":2663},{"style":136},[2664],{"type":34,"value":1231},{"type":25,"tag":129,"props":2666,"children":2667},{"class":131,"line":204},[2668,2672,2677,2682,2687,2691,2696],{"type":25,"tag":129,"props":2669,"children":2670},{"style":136},[2671],{"type":34,"value":2646},{"type":25,"tag":129,"props":2673,"children":2674},{"style":153},[2675],{"type":34,"value":2676},"waitDurationInOpenState",{"type":25,"tag":129,"props":2678,"children":2679},{"style":136},[2680],{"type":34,"value":2681},"(Duration.",{"type":25,"tag":129,"props":2683,"children":2684},{"style":153},[2685],{"type":34,"value":2686},"ofMillis",{"type":25,"tag":129,"props":2688,"children":2689},{"style":136},[2690],{"type":34,"value":161},{"type":25,"tag":129,"props":2692,"children":2693},{"style":193},[2694],{"type":34,"value":2695},"1000",{"type":25,"tag":129,"props":2697,"children":2698},{"style":136},[2699],{"type":34,"value":2700},"))\n",{"type":25,"tag":129,"props":2702,"children":2703},{"class":131,"line":230},[2704,2708,2713,2717,2721],{"type":25,"tag":129,"props":2705,"children":2706},{"style":136},[2707],{"type":34,"value":2646},{"type":25,"tag":129,"props":2709,"children":2710},{"style":153},[2711],{"type":34,"value":2712},"permittedNumberOfCallsInHalfOpenState",{"type":25,"tag":129,"props":2714,"children":2715},{"style":136},[2716],{"type":34,"value":161},{"type":25,"tag":129,"props":2718,"children":2719},{"style":193},[2720],{"type":34,"value":222},{"type":25,"tag":129,"props":2722,"children":2723},{"style":136},[2724],{"type":34,"value":1231},{"type":25,"tag":129,"props":2726,"children":2727},{"class":131,"line":363},[2728,2732,2737,2741,2746],{"type":25,"tag":129,"props":2729,"children":2730},{"style":136},[2731],{"type":34,"value":2646},{"type":25,"tag":129,"props":2733,"children":2734},{"style":153},[2735],{"type":34,"value":2736},"minimumNumberOfCalls",{"type":25,"tag":129,"props":2738,"children":2739},{"style":136},[2740],{"type":34,"value":161},{"type":25,"tag":129,"props":2742,"children":2743},{"style":193},[2744],{"type":34,"value":2745},"5",{"type":25,"tag":129,"props":2747,"children":2748},{"style":136},[2749],{"type":34,"value":1231},{"type":25,"tag":129,"props":2751,"children":2752},{"class":131,"line":373},[2753,2757,2762],{"type":25,"tag":129,"props":2754,"children":2755},{"style":136},[2756],{"type":34,"value":2646},{"type":25,"tag":129,"props":2758,"children":2759},{"style":153},[2760],{"type":34,"value":2761},"build",{"type":25,"tag":129,"props":2763,"children":2764},{"style":136},[2765],{"type":34,"value":255},{"type":25,"tag":129,"props":2767,"children":2768},{"class":131,"line":1197},[2769],{"type":25,"tag":129,"props":2770,"children":2771},{"emptyLinePlaceholder":297},[2772],{"type":34,"value":300},{"type":25,"tag":129,"props":2774,"children":2775},{"class":131,"line":1205},[2776,2781,2785,2790,2795,2799,2804],{"type":25,"tag":129,"props":2777,"children":2778},{"style":136},[2779],{"type":34,"value":2780},"CircuitBreaker circuitBreaker ",{"type":25,"tag":129,"props":2782,"children":2783},{"style":142},[2784],{"type":34,"value":145},{"type":25,"tag":129,"props":2786,"children":2787},{"style":136},[2788],{"type":34,"value":2789}," CircuitBreaker.",{"type":25,"tag":129,"props":2791,"children":2792},{"style":153},[2793],{"type":34,"value":2794},"of",{"type":25,"tag":129,"props":2796,"children":2797},{"style":136},[2798],{"type":34,"value":161},{"type":25,"tag":129,"props":2800,"children":2801},{"style":164},[2802],{"type":34,"value":2803},"\"myService\"",{"type":25,"tag":129,"props":2805,"children":2806},{"style":136},[2807],{"type":34,"value":2808},", config);\n",{"type":25,"tag":2478,"props":2810,"children":2812},{"id":2811},"step-3-using-circuit-breaker",[2813],{"type":34,"value":2814},"Step 3: Using Circuit Breaker",{"type":25,"tag":30,"props":2816,"children":2817},{},[2818],{"type":34,"value":2819},"Wrap service calls using the circuit breaker:",{"type":25,"tag":120,"props":2821,"children":2823},{"className":122,"code":2822,"language":16,"meta":7,"style":7},"Supplier\u003CString> decoratedSupplier = CircuitBreaker.decorateSupplier(circuitBreaker, () -> myService.remoteCall());\n\nTry.ofSupplier(decoratedSupplier)\n    .recover(throwable -> \"Fallback response\")\n    .onSuccess(result -> System.out.println(\"Response: \" + result));\n",[2824],{"type":25,"tag":14,"props":2825,"children":2826},{"__ignoreMap":7},[2827,2882,2889,2907,2937],{"type":25,"tag":129,"props":2828,"children":2829},{"class":131,"line":132},[2830,2835,2840,2845,2849,2853,2858,2863,2868,2873,2878],{"type":25,"tag":129,"props":2831,"children":2832},{"style":136},[2833],{"type":34,"value":2834},"Supplier\u003C",{"type":25,"tag":129,"props":2836,"children":2837},{"style":142},[2838],{"type":34,"value":2839},"String",{"type":25,"tag":129,"props":2841,"children":2842},{"style":136},[2843],{"type":34,"value":2844},"> decoratedSupplier ",{"type":25,"tag":129,"props":2846,"children":2847},{"style":142},[2848],{"type":34,"value":145},{"type":25,"tag":129,"props":2850,"children":2851},{"style":136},[2852],{"type":34,"value":2789},{"type":25,"tag":129,"props":2854,"children":2855},{"style":153},[2856],{"type":34,"value":2857},"decorateSupplier",{"type":25,"tag":129,"props":2859,"children":2860},{"style":136},[2861],{"type":34,"value":2862},"(circuitBreaker, () ",{"type":25,"tag":129,"props":2864,"children":2865},{"style":142},[2866],{"type":34,"value":2867},"->",{"type":25,"tag":129,"props":2869,"children":2870},{"style":136},[2871],{"type":34,"value":2872}," myService.",{"type":25,"tag":129,"props":2874,"children":2875},{"style":153},[2876],{"type":34,"value":2877},"remoteCall",{"type":25,"tag":129,"props":2879,"children":2880},{"style":136},[2881],{"type":34,"value":337},{"type":25,"tag":129,"props":2883,"children":2884},{"class":131,"line":175},[2885],{"type":25,"tag":129,"props":2886,"children":2887},{"emptyLinePlaceholder":297},[2888],{"type":34,"value":300},{"type":25,"tag":129,"props":2890,"children":2891},{"class":131,"line":204},[2892,2897,2902],{"type":25,"tag":129,"props":2893,"children":2894},{"style":136},[2895],{"type":34,"value":2896},"Try.",{"type":25,"tag":129,"props":2898,"children":2899},{"style":153},[2900],{"type":34,"value":2901},"ofSupplier",{"type":25,"tag":129,"props":2903,"children":2904},{"style":136},[2905],{"type":34,"value":2906},"(decoratedSupplier)\n",{"type":25,"tag":129,"props":2908,"children":2909},{"class":131,"line":230},[2910,2914,2919,2924,2928,2933],{"type":25,"tag":129,"props":2911,"children":2912},{"style":136},[2913],{"type":34,"value":2646},{"type":25,"tag":129,"props":2915,"children":2916},{"style":153},[2917],{"type":34,"value":2918},"recover",{"type":25,"tag":129,"props":2920,"children":2921},{"style":136},[2922],{"type":34,"value":2923},"(throwable ",{"type":25,"tag":129,"props":2925,"children":2926},{"style":142},[2927],{"type":34,"value":2867},{"type":25,"tag":129,"props":2929,"children":2930},{"style":164},[2931],{"type":34,"value":2932}," \"Fallback response\"",{"type":25,"tag":129,"props":2934,"children":2935},{"style":136},[2936],{"type":34,"value":1231},{"type":25,"tag":129,"props":2938,"children":2939},{"class":131,"line":363},[2940,2944,2949,2954,2958,2963,2968,2972,2977,2982],{"type":25,"tag":129,"props":2941,"children":2942},{"style":136},[2943],{"type":34,"value":2646},{"type":25,"tag":129,"props":2945,"children":2946},{"style":153},[2947],{"type":34,"value":2948},"onSuccess",{"type":25,"tag":129,"props":2950,"children":2951},{"style":136},[2952],{"type":34,"value":2953},"(result ",{"type":25,"tag":129,"props":2955,"children":2956},{"style":142},[2957],{"type":34,"value":2867},{"type":25,"tag":129,"props":2959,"children":2960},{"style":136},[2961],{"type":34,"value":2962}," System.out.",{"type":25,"tag":129,"props":2964,"children":2965},{"style":153},[2966],{"type":34,"value":2967},"println",{"type":25,"tag":129,"props":2969,"children":2970},{"style":136},[2971],{"type":34,"value":161},{"type":25,"tag":129,"props":2973,"children":2974},{"style":164},[2975],{"type":34,"value":2976},"\"Response: \"",{"type":25,"tag":129,"props":2978,"children":2979},{"style":142},[2980],{"type":34,"value":2981}," +",{"type":25,"tag":129,"props":2983,"children":2984},{"style":136},[2985],{"type":34,"value":2986}," result));\n",{"type":25,"tag":37,"props":2988,"children":2990},{"id":2989},"monitoring-and-metrics",[2991],{"type":34,"value":2992},"Monitoring and Metrics",{"type":25,"tag":30,"props":2994,"children":2995},{},[2996],{"type":34,"value":2997},"Resilience4j provides built-in support for metrics and monitoring:",{"type":25,"tag":120,"props":2999,"children":3001},{"className":122,"code":3000,"language":16,"meta":7,"style":7},"CircuitBreakerRegistry registry = CircuitBreakerRegistry.ofDefaults();\nregistry.getEventPublisher()\n    .onStateTransition(event -> System.out.println(event.getStateTransition()));\n",[3002],{"type":25,"tag":14,"props":3003,"children":3004},{"__ignoreMap":7},[3005,3031,3048],{"type":25,"tag":129,"props":3006,"children":3007},{"class":131,"line":132},[3008,3013,3017,3022,3027],{"type":25,"tag":129,"props":3009,"children":3010},{"style":136},[3011],{"type":34,"value":3012},"CircuitBreakerRegistry registry ",{"type":25,"tag":129,"props":3014,"children":3015},{"style":142},[3016],{"type":34,"value":145},{"type":25,"tag":129,"props":3018,"children":3019},{"style":136},[3020],{"type":34,"value":3021}," CircuitBreakerRegistry.",{"type":25,"tag":129,"props":3023,"children":3024},{"style":153},[3025],{"type":34,"value":3026},"ofDefaults",{"type":25,"tag":129,"props":3028,"children":3029},{"style":136},[3030],{"type":34,"value":255},{"type":25,"tag":129,"props":3032,"children":3033},{"class":131,"line":175},[3034,3039,3044],{"type":25,"tag":129,"props":3035,"children":3036},{"style":136},[3037],{"type":34,"value":3038},"registry.",{"type":25,"tag":129,"props":3040,"children":3041},{"style":153},[3042],{"type":34,"value":3043},"getEventPublisher",{"type":25,"tag":129,"props":3045,"children":3046},{"style":136},[3047],{"type":34,"value":2638},{"type":25,"tag":129,"props":3049,"children":3050},{"class":131,"line":204},[3051,3055,3060,3065,3069,3073,3077,3082,3087],{"type":25,"tag":129,"props":3052,"children":3053},{"style":136},[3054],{"type":34,"value":2646},{"type":25,"tag":129,"props":3056,"children":3057},{"style":153},[3058],{"type":34,"value":3059},"onStateTransition",{"type":25,"tag":129,"props":3061,"children":3062},{"style":136},[3063],{"type":34,"value":3064},"(event ",{"type":25,"tag":129,"props":3066,"children":3067},{"style":142},[3068],{"type":34,"value":2867},{"type":25,"tag":129,"props":3070,"children":3071},{"style":136},[3072],{"type":34,"value":2962},{"type":25,"tag":129,"props":3074,"children":3075},{"style":153},[3076],{"type":34,"value":2967},{"type":25,"tag":129,"props":3078,"children":3079},{"style":136},[3080],{"type":34,"value":3081},"(event.",{"type":25,"tag":129,"props":3083,"children":3084},{"style":153},[3085],{"type":34,"value":3086},"getStateTransition",{"type":25,"tag":129,"props":3088,"children":3089},{"style":136},[3090],{"type":34,"value":3091},"()));\n",{"type":25,"tag":30,"props":3093,"children":3094},{},[3095],{"type":34,"value":3096},"Integrate with Prometheus, Grafana, or other observability tools for comprehensive monitoring.",{"type":25,"tag":37,"props":3098,"children":3100},{"id":3099},"best-practices-for-circuit-breaking",[3101],{"type":34,"value":3102},"Best Practices for Circuit Breaking",{"type":25,"tag":895,"props":3104,"children":3105},{},[3106,3111,3116,3121],{"type":25,"tag":53,"props":3107,"children":3108},{},[3109],{"type":34,"value":3110},"Configure sensible thresholds to avoid premature circuit opening.",{"type":25,"tag":53,"props":3112,"children":3113},{},[3114],{"type":34,"value":3115},"Always define fallback mechanisms.",{"type":25,"tag":53,"props":3117,"children":3118},{},[3119],{"type":34,"value":3120},"Regularly monitor circuit breaker states and metrics.",{"type":25,"tag":53,"props":3122,"children":3123},{},[3124],{"type":34,"value":3125},"Test thoroughly to ensure reliability under failure conditions.",{"type":25,"tag":37,"props":3127,"children":3128},{"id":878},[3129],{"type":34,"value":881},{"type":25,"tag":30,"props":3131,"children":3132},{},[3133],{"type":34,"value":3134},"Implementing circuit breakers using Resilience4j significantly enhances the resilience of your Java-based distributed systems. This proactive approach ensures your systems gracefully handle failures, maintaining service availability and user satisfaction.",{"type":25,"tag":888,"props":3136,"children":3137},{"id":890},[3138],{"type":34,"value":893},{"type":25,"tag":895,"props":3140,"children":3141},{},[3142,3152,3162],{"type":25,"tag":53,"props":3143,"children":3144},{},[3145],{"type":25,"tag":902,"props":3146,"children":3149},{"href":3147,"rel":3148},"https://resilience4j.readme.io/docs",[906],[3150],{"type":34,"value":3151},"Resilience4j Official Documentation",{"type":25,"tag":53,"props":3153,"children":3154},{},[3155],{"type":25,"tag":902,"props":3156,"children":3159},{"href":3157,"rel":3158},"https://martinfowler.com/bliki/CircuitBreaker.html",[906],[3160],{"type":34,"value":3161},"Circuit Breaker Pattern by Martin Fowler",{"type":25,"tag":53,"props":3163,"children":3164},{},[3165],{"type":25,"tag":902,"props":3166,"children":3169},{"href":3167,"rel":3168},"https://microservices.io/patterns/reliability/circuit-breaker.html",[906],[3170],{"type":34,"value":3171},"Microservices Patterns by Chris Richardson",{"type":25,"tag":931,"props":3173,"children":3174},{},[3175],{"type":34,"value":935},{"title":7,"searchDepth":175,"depth":175,"links":3177},[3178,3179,3180,3185,3186,3187],{"id":2394,"depth":175,"text":2397},{"id":2444,"depth":175,"text":2447},{"id":2473,"depth":175,"text":2476,"children":3181},[3182,3183,3184],{"id":2480,"depth":204,"text":2483},{"id":2601,"depth":204,"text":2604},{"id":2811,"depth":204,"text":2814},{"id":2989,"depth":175,"text":2992},{"id":3099,"depth":175,"text":3102},{"id":878,"depth":175,"text":881},"content:posts:circuit-breaking-resilience.md","posts/circuit-breaking-resilience.md","posts/circuit-breaking-resilience",{"_path":3192,"_dir":5,"_draft":6,"_partial":6,"_locale":7,"title":3193,"description":3194,"date":3195,"layout":11,"subtitle":3196,"image":3197,"optimized_image":3197,"category":14,"tags":3198,"author":20,"paginate":6,"body":3202,"_type":948,"_id":4198,"_source":950,"_file":4199,"_stem":4200,"_extension":953},"/posts/maven-and-github-actions","Automating Java Builds with Maven and GitHub Actions CI/CD","Learn how to set up automated Java build pipelines using Maven and GitHub Actions, including practical examples and detailed instructions.","2024-06-15T11:00:00.000Z","A Step-by-Step Guide to Continuous Integration and Deployment","/assets/img/uploads/java-maven-github-actions.png",[14,16,3199,3200,3201],"maven","github-actions","cicd",{"type":22,"children":3203,"toc":4187},[3204,3226,3232,3253,3259,3264,3272,3285,3616,3622,3681,3687,3692,3852,3858,3863,3935,3947,3953,3958,4017,4029,4035,4058,4064,4069,4124,4137,4141,4146,4150,4183],{"type":25,"tag":26,"props":3205,"children":3206},{},[3207],{"type":25,"tag":30,"props":3208,"children":3209},{},[3210,3212,3217,3219,3224],{"type":34,"value":3211},"Continuous Integration and Continuous Deployment (CI/CD) streamline development workflows, improve software quality, and accelerate delivery. This tutorial guides you through setting up automated Java builds using ",{"type":25,"tag":2410,"props":3213,"children":3214},{},[3215],{"type":34,"value":3216},"Maven",{"type":34,"value":3218}," and ",{"type":25,"tag":2410,"props":3220,"children":3221},{},[3222],{"type":34,"value":3223},"GitHub Actions",{"type":34,"value":3225},".",{"type":25,"tag":37,"props":3227,"children":3229},{"id":3228},"prerequisites",[3230],{"type":34,"value":3231},"Prerequisites",{"type":25,"tag":895,"props":3233,"children":3234},{},[3235,3248],{"type":25,"tag":53,"props":3236,"children":3237},{},[3238,3240,3246],{"type":34,"value":3239},"A Java project with Maven configured (",{"type":25,"tag":14,"props":3241,"children":3243},{"className":3242},[],[3244],{"type":34,"value":3245},"pom.xml",{"type":34,"value":3247},").",{"type":25,"tag":53,"props":3249,"children":3250},{},[3251],{"type":34,"value":3252},"GitHub repository.",{"type":25,"tag":37,"props":3254,"children":3256},{"id":3255},"step-1-setting-up-your-github-actions-workflow",[3257],{"type":34,"value":3258},"Step 1: Setting Up Your GitHub Actions Workflow",{"type":25,"tag":30,"props":3260,"children":3261},{},[3262],{"type":34,"value":3263},"In your repository, create the following directory structure:",{"type":25,"tag":120,"props":3265,"children":3267},{"code":3266},".github/workflows/\n",[3268],{"type":25,"tag":14,"props":3269,"children":3270},{"__ignoreMap":7},[3271],{"type":34,"value":3266},{"type":25,"tag":30,"props":3273,"children":3274},{},[3275,3277,3283],{"type":34,"value":3276},"Create a new file named ",{"type":25,"tag":14,"props":3278,"children":3280},{"className":3279},[],[3281],{"type":34,"value":3282},"maven-ci.yml",{"type":34,"value":3284}," within this directory:",{"type":25,"tag":120,"props":3286,"children":3290},{"code":3287,"language":3288,"meta":7,"className":3289,"style":7},"name: Maven CI\n\non:\n  push:\n    branches: [ \"main\" ]\n  pull_request:\n    branches: [ \"main\" ]\n\njobs:\n  build:\n    runs-on: ubuntu-latest\n\n    steps:\n      - uses: actions/checkout@v4\n      - name: Set up JDK 21\n        uses: actions/setup-java@v4\n        with:\n          java-version: '21'\n          distribution: 'temurin'\n\n      - name: Build with Maven\n        run: mvn clean install\n","yml","language-yml shiki shiki-themes github-dark github-light",[3291],{"type":25,"tag":14,"props":3292,"children":3293},{"__ignoreMap":7},[3294,3311,3318,3330,3342,3365,3377,3396,3403,3415,3427,3444,3451,3463,3485,3505,3522,3534,3551,3569,3577,3598],{"type":25,"tag":129,"props":3295,"children":3296},{"class":131,"line":132},[3297,3302,3306],{"type":25,"tag":129,"props":3298,"children":3299},{"style":721},[3300],{"type":34,"value":3301},"name",{"type":25,"tag":129,"props":3303,"children":3304},{"style":136},[3305],{"type":34,"value":1826},{"type":25,"tag":129,"props":3307,"children":3308},{"style":164},[3309],{"type":34,"value":3310},"Maven CI\n",{"type":25,"tag":129,"props":3312,"children":3313},{"class":131,"line":175},[3314],{"type":25,"tag":129,"props":3315,"children":3316},{"emptyLinePlaceholder":297},[3317],{"type":34,"value":300},{"type":25,"tag":129,"props":3319,"children":3320},{"class":131,"line":204},[3321,3326],{"type":25,"tag":129,"props":3322,"children":3323},{"style":193},[3324],{"type":34,"value":3325},"on",{"type":25,"tag":129,"props":3327,"children":3328},{"style":136},[3329],{"type":34,"value":2135},{"type":25,"tag":129,"props":3331,"children":3332},{"class":131,"line":230},[3333,3338],{"type":25,"tag":129,"props":3334,"children":3335},{"style":721},[3336],{"type":34,"value":3337},"  push",{"type":25,"tag":129,"props":3339,"children":3340},{"style":136},[3341],{"type":34,"value":2135},{"type":25,"tag":129,"props":3343,"children":3344},{"class":131,"line":363},[3345,3350,3355,3360],{"type":25,"tag":129,"props":3346,"children":3347},{"style":721},[3348],{"type":34,"value":3349},"    branches",{"type":25,"tag":129,"props":3351,"children":3352},{"style":136},[3353],{"type":34,"value":3354},": [ ",{"type":25,"tag":129,"props":3356,"children":3357},{"style":164},[3358],{"type":34,"value":3359},"\"main\"",{"type":25,"tag":129,"props":3361,"children":3362},{"style":136},[3363],{"type":34,"value":3364}," ]\n",{"type":25,"tag":129,"props":3366,"children":3367},{"class":131,"line":373},[3368,3373],{"type":25,"tag":129,"props":3369,"children":3370},{"style":721},[3371],{"type":34,"value":3372},"  pull_request",{"type":25,"tag":129,"props":3374,"children":3375},{"style":136},[3376],{"type":34,"value":2135},{"type":25,"tag":129,"props":3378,"children":3379},{"class":131,"line":1197},[3380,3384,3388,3392],{"type":25,"tag":129,"props":3381,"children":3382},{"style":721},[3383],{"type":34,"value":3349},{"type":25,"tag":129,"props":3385,"children":3386},{"style":136},[3387],{"type":34,"value":3354},{"type":25,"tag":129,"props":3389,"children":3390},{"style":164},[3391],{"type":34,"value":3359},{"type":25,"tag":129,"props":3393,"children":3394},{"style":136},[3395],{"type":34,"value":3364},{"type":25,"tag":129,"props":3397,"children":3398},{"class":131,"line":1205},[3399],{"type":25,"tag":129,"props":3400,"children":3401},{"emptyLinePlaceholder":297},[3402],{"type":34,"value":300},{"type":25,"tag":129,"props":3404,"children":3405},{"class":131,"line":1234},[3406,3411],{"type":25,"tag":129,"props":3407,"children":3408},{"style":721},[3409],{"type":34,"value":3410},"jobs",{"type":25,"tag":129,"props":3412,"children":3413},{"style":136},[3414],{"type":34,"value":2135},{"type":25,"tag":129,"props":3416,"children":3417},{"class":131,"line":1260},[3418,3423],{"type":25,"tag":129,"props":3419,"children":3420},{"style":721},[3421],{"type":34,"value":3422},"  build",{"type":25,"tag":129,"props":3424,"children":3425},{"style":136},[3426],{"type":34,"value":2135},{"type":25,"tag":129,"props":3428,"children":3429},{"class":131,"line":1293},[3430,3435,3439],{"type":25,"tag":129,"props":3431,"children":3432},{"style":721},[3433],{"type":34,"value":3434},"    runs-on",{"type":25,"tag":129,"props":3436,"children":3437},{"style":136},[3438],{"type":34,"value":1826},{"type":25,"tag":129,"props":3440,"children":3441},{"style":164},[3442],{"type":34,"value":3443},"ubuntu-latest\n",{"type":25,"tag":129,"props":3445,"children":3446},{"class":131,"line":1618},[3447],{"type":25,"tag":129,"props":3448,"children":3449},{"emptyLinePlaceholder":297},[3450],{"type":34,"value":300},{"type":25,"tag":129,"props":3452,"children":3453},{"class":131,"line":1626},[3454,3459],{"type":25,"tag":129,"props":3455,"children":3456},{"style":721},[3457],{"type":34,"value":3458},"    steps",{"type":25,"tag":129,"props":3460,"children":3461},{"style":136},[3462],{"type":34,"value":2135},{"type":25,"tag":129,"props":3464,"children":3465},{"class":131,"line":1644},[3466,3471,3476,3480],{"type":25,"tag":129,"props":3467,"children":3468},{"style":136},[3469],{"type":34,"value":3470},"      - ",{"type":25,"tag":129,"props":3472,"children":3473},{"style":721},[3474],{"type":34,"value":3475},"uses",{"type":25,"tag":129,"props":3477,"children":3478},{"style":136},[3479],{"type":34,"value":1826},{"type":25,"tag":129,"props":3481,"children":3482},{"style":164},[3483],{"type":34,"value":3484},"actions/checkout@v4\n",{"type":25,"tag":129,"props":3486,"children":3487},{"class":131,"line":1958},[3488,3492,3496,3500],{"type":25,"tag":129,"props":3489,"children":3490},{"style":136},[3491],{"type":34,"value":3470},{"type":25,"tag":129,"props":3493,"children":3494},{"style":721},[3495],{"type":34,"value":3301},{"type":25,"tag":129,"props":3497,"children":3498},{"style":136},[3499],{"type":34,"value":1826},{"type":25,"tag":129,"props":3501,"children":3502},{"style":164},[3503],{"type":34,"value":3504},"Set up JDK 21\n",{"type":25,"tag":129,"props":3506,"children":3507},{"class":131,"line":1971},[3508,3513,3517],{"type":25,"tag":129,"props":3509,"children":3510},{"style":721},[3511],{"type":34,"value":3512},"        uses",{"type":25,"tag":129,"props":3514,"children":3515},{"style":136},[3516],{"type":34,"value":1826},{"type":25,"tag":129,"props":3518,"children":3519},{"style":164},[3520],{"type":34,"value":3521},"actions/setup-java@v4\n",{"type":25,"tag":129,"props":3523,"children":3524},{"class":131,"line":1979},[3525,3530],{"type":25,"tag":129,"props":3526,"children":3527},{"style":721},[3528],{"type":34,"value":3529},"        with",{"type":25,"tag":129,"props":3531,"children":3532},{"style":136},[3533],{"type":34,"value":2135},{"type":25,"tag":129,"props":3535,"children":3536},{"class":131,"line":2007},[3537,3542,3546],{"type":25,"tag":129,"props":3538,"children":3539},{"style":721},[3540],{"type":34,"value":3541},"          java-version",{"type":25,"tag":129,"props":3543,"children":3544},{"style":136},[3545],{"type":34,"value":1826},{"type":25,"tag":129,"props":3547,"children":3548},{"style":164},[3549],{"type":34,"value":3550},"'21'\n",{"type":25,"tag":129,"props":3552,"children":3554},{"class":131,"line":3553},19,[3555,3560,3564],{"type":25,"tag":129,"props":3556,"children":3557},{"style":721},[3558],{"type":34,"value":3559},"          distribution",{"type":25,"tag":129,"props":3561,"children":3562},{"style":136},[3563],{"type":34,"value":1826},{"type":25,"tag":129,"props":3565,"children":3566},{"style":164},[3567],{"type":34,"value":3568},"'temurin'\n",{"type":25,"tag":129,"props":3570,"children":3572},{"class":131,"line":3571},20,[3573],{"type":25,"tag":129,"props":3574,"children":3575},{"emptyLinePlaceholder":297},[3576],{"type":34,"value":300},{"type":25,"tag":129,"props":3578,"children":3580},{"class":131,"line":3579},21,[3581,3585,3589,3593],{"type":25,"tag":129,"props":3582,"children":3583},{"style":136},[3584],{"type":34,"value":3470},{"type":25,"tag":129,"props":3586,"children":3587},{"style":721},[3588],{"type":34,"value":3301},{"type":25,"tag":129,"props":3590,"children":3591},{"style":136},[3592],{"type":34,"value":1826},{"type":25,"tag":129,"props":3594,"children":3595},{"style":164},[3596],{"type":34,"value":3597},"Build with Maven\n",{"type":25,"tag":129,"props":3599,"children":3601},{"class":131,"line":3600},22,[3602,3607,3611],{"type":25,"tag":129,"props":3603,"children":3604},{"style":721},[3605],{"type":34,"value":3606},"        run",{"type":25,"tag":129,"props":3608,"children":3609},{"style":136},[3610],{"type":34,"value":1826},{"type":25,"tag":129,"props":3612,"children":3613},{"style":164},[3614],{"type":34,"value":3615},"mvn clean install\n",{"type":25,"tag":37,"props":3617,"children":3619},{"id":3618},"step-2-understanding-the-workflow",[3620],{"type":34,"value":3621},"Step 2: Understanding the Workflow",{"type":25,"tag":895,"props":3623,"children":3624},{},[3625,3643,3653,3663],{"type":25,"tag":53,"props":3626,"children":3627},{},[3628,3633,3635,3641],{"type":25,"tag":2410,"props":3629,"children":3630},{},[3631],{"type":34,"value":3632},"Trigger:",{"type":34,"value":3634}," Activated on push or pull request to the ",{"type":25,"tag":14,"props":3636,"children":3638},{"className":3637},[],[3639],{"type":34,"value":3640},"main",{"type":34,"value":3642}," branch.",{"type":25,"tag":53,"props":3644,"children":3645},{},[3646,3651],{"type":25,"tag":2410,"props":3647,"children":3648},{},[3649],{"type":34,"value":3650},"Checkout:",{"type":34,"value":3652}," Retrieves the source code from your repository.",{"type":25,"tag":53,"props":3654,"children":3655},{},[3656,3661],{"type":25,"tag":2410,"props":3657,"children":3658},{},[3659],{"type":34,"value":3660},"JDK Setup:",{"type":34,"value":3662}," Installs Java 21 from Temurin.",{"type":25,"tag":53,"props":3664,"children":3665},{},[3666,3671,3673,3679],{"type":25,"tag":2410,"props":3667,"children":3668},{},[3669],{"type":34,"value":3670},"Maven Build:",{"type":34,"value":3672}," Executes Maven goals (",{"type":25,"tag":14,"props":3674,"children":3676},{"className":3675},[],[3677],{"type":34,"value":3678},"clean install",{"type":34,"value":3680},") to compile, test, and package your Java application.",{"type":25,"tag":37,"props":3682,"children":3684},{"id":3683},"step-3-add-maven-test-reports",[3685],{"type":34,"value":3686},"Step 3: Add Maven Test Reports",{"type":25,"tag":30,"props":3688,"children":3689},{},[3690],{"type":34,"value":3691},"Enhance your workflow by generating and uploading test reports:",{"type":25,"tag":120,"props":3693,"children":3695},{"code":3694,"language":3288,"meta":7,"className":3289,"style":7},"- name: Run tests and upload reports\n  run: |\n    mvn test\n  continue-on-error: true\n\n- name: Upload test report\n  uses: actions/upload-artifact@v4\n  with:\n    name: test-report\n    path: target/surefire-reports/\n",[3696],{"type":25,"tag":14,"props":3697,"children":3698},{"__ignoreMap":7},[3699,3720,3737,3745,3762,3769,3789,3806,3818,3835],{"type":25,"tag":129,"props":3700,"children":3701},{"class":131,"line":132},[3702,3707,3711,3715],{"type":25,"tag":129,"props":3703,"children":3704},{"style":136},[3705],{"type":34,"value":3706},"- ",{"type":25,"tag":129,"props":3708,"children":3709},{"style":721},[3710],{"type":34,"value":3301},{"type":25,"tag":129,"props":3712,"children":3713},{"style":136},[3714],{"type":34,"value":1826},{"type":25,"tag":129,"props":3716,"children":3717},{"style":164},[3718],{"type":34,"value":3719},"Run tests and upload reports\n",{"type":25,"tag":129,"props":3721,"children":3722},{"class":131,"line":175},[3723,3728,3732],{"type":25,"tag":129,"props":3724,"children":3725},{"style":721},[3726],{"type":34,"value":3727},"  run",{"type":25,"tag":129,"props":3729,"children":3730},{"style":136},[3731],{"type":34,"value":1826},{"type":25,"tag":129,"props":3733,"children":3734},{"style":142},[3735],{"type":34,"value":3736},"|\n",{"type":25,"tag":129,"props":3738,"children":3739},{"class":131,"line":204},[3740],{"type":25,"tag":129,"props":3741,"children":3742},{"style":164},[3743],{"type":34,"value":3744},"    mvn test\n",{"type":25,"tag":129,"props":3746,"children":3747},{"class":131,"line":230},[3748,3753,3757],{"type":25,"tag":129,"props":3749,"children":3750},{"style":721},[3751],{"type":34,"value":3752},"  continue-on-error",{"type":25,"tag":129,"props":3754,"children":3755},{"style":136},[3756],{"type":34,"value":1826},{"type":25,"tag":129,"props":3758,"children":3759},{"style":193},[3760],{"type":34,"value":3761},"true\n",{"type":25,"tag":129,"props":3763,"children":3764},{"class":131,"line":363},[3765],{"type":25,"tag":129,"props":3766,"children":3767},{"emptyLinePlaceholder":297},[3768],{"type":34,"value":300},{"type":25,"tag":129,"props":3770,"children":3771},{"class":131,"line":373},[3772,3776,3780,3784],{"type":25,"tag":129,"props":3773,"children":3774},{"style":136},[3775],{"type":34,"value":3706},{"type":25,"tag":129,"props":3777,"children":3778},{"style":721},[3779],{"type":34,"value":3301},{"type":25,"tag":129,"props":3781,"children":3782},{"style":136},[3783],{"type":34,"value":1826},{"type":25,"tag":129,"props":3785,"children":3786},{"style":164},[3787],{"type":34,"value":3788},"Upload test report\n",{"type":25,"tag":129,"props":3790,"children":3791},{"class":131,"line":1197},[3792,3797,3801],{"type":25,"tag":129,"props":3793,"children":3794},{"style":721},[3795],{"type":34,"value":3796},"  uses",{"type":25,"tag":129,"props":3798,"children":3799},{"style":136},[3800],{"type":34,"value":1826},{"type":25,"tag":129,"props":3802,"children":3803},{"style":164},[3804],{"type":34,"value":3805},"actions/upload-artifact@v4\n",{"type":25,"tag":129,"props":3807,"children":3808},{"class":131,"line":1205},[3809,3814],{"type":25,"tag":129,"props":3810,"children":3811},{"style":721},[3812],{"type":34,"value":3813},"  with",{"type":25,"tag":129,"props":3815,"children":3816},{"style":136},[3817],{"type":34,"value":2135},{"type":25,"tag":129,"props":3819,"children":3820},{"class":131,"line":1234},[3821,3826,3830],{"type":25,"tag":129,"props":3822,"children":3823},{"style":721},[3824],{"type":34,"value":3825},"    name",{"type":25,"tag":129,"props":3827,"children":3828},{"style":136},[3829],{"type":34,"value":1826},{"type":25,"tag":129,"props":3831,"children":3832},{"style":164},[3833],{"type":34,"value":3834},"test-report\n",{"type":25,"tag":129,"props":3836,"children":3837},{"class":131,"line":1260},[3838,3843,3847],{"type":25,"tag":129,"props":3839,"children":3840},{"style":721},[3841],{"type":34,"value":3842},"    path",{"type":25,"tag":129,"props":3844,"children":3845},{"style":136},[3846],{"type":34,"value":1826},{"type":25,"tag":129,"props":3848,"children":3849},{"style":164},[3850],{"type":34,"value":3851},"target/surefire-reports/\n",{"type":25,"tag":37,"props":3853,"children":3855},{"id":3854},"step-4-deploy-artifacts-optional",[3856],{"type":34,"value":3857},"Step 4: Deploy Artifacts (Optional)",{"type":25,"tag":30,"props":3859,"children":3860},{},[3861],{"type":34,"value":3862},"To automatically deploy artifacts, include the deployment steps:",{"type":25,"tag":120,"props":3864,"children":3866},{"code":3865,"language":3288,"meta":7,"className":3289,"style":7},"- name: Deploy package\n  env:\n    GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}\n  run: mvn deploy\n",[3867],{"type":25,"tag":14,"props":3868,"children":3869},{"__ignoreMap":7},[3870,3890,3902,3919],{"type":25,"tag":129,"props":3871,"children":3872},{"class":131,"line":132},[3873,3877,3881,3885],{"type":25,"tag":129,"props":3874,"children":3875},{"style":136},[3876],{"type":34,"value":3706},{"type":25,"tag":129,"props":3878,"children":3879},{"style":721},[3880],{"type":34,"value":3301},{"type":25,"tag":129,"props":3882,"children":3883},{"style":136},[3884],{"type":34,"value":1826},{"type":25,"tag":129,"props":3886,"children":3887},{"style":164},[3888],{"type":34,"value":3889},"Deploy package\n",{"type":25,"tag":129,"props":3891,"children":3892},{"class":131,"line":175},[3893,3898],{"type":25,"tag":129,"props":3894,"children":3895},{"style":721},[3896],{"type":34,"value":3897},"  env",{"type":25,"tag":129,"props":3899,"children":3900},{"style":136},[3901],{"type":34,"value":2135},{"type":25,"tag":129,"props":3903,"children":3904},{"class":131,"line":204},[3905,3910,3914],{"type":25,"tag":129,"props":3906,"children":3907},{"style":721},[3908],{"type":34,"value":3909},"    GITHUB_TOKEN",{"type":25,"tag":129,"props":3911,"children":3912},{"style":136},[3913],{"type":34,"value":1826},{"type":25,"tag":129,"props":3915,"children":3916},{"style":164},[3917],{"type":34,"value":3918},"${{ secrets.GITHUB_TOKEN }}\n",{"type":25,"tag":129,"props":3920,"children":3921},{"class":131,"line":230},[3922,3926,3930],{"type":25,"tag":129,"props":3923,"children":3924},{"style":721},[3925],{"type":34,"value":3727},{"type":25,"tag":129,"props":3927,"children":3928},{"style":136},[3929],{"type":34,"value":1826},{"type":25,"tag":129,"props":3931,"children":3932},{"style":164},[3933],{"type":34,"value":3934},"mvn deploy\n",{"type":25,"tag":30,"props":3936,"children":3937},{},[3938,3940,3945],{"type":34,"value":3939},"Ensure your ",{"type":25,"tag":14,"props":3941,"children":3943},{"className":3942},[],[3944],{"type":34,"value":3245},{"type":34,"value":3946}," is configured for deployment (e.g., GitHub Packages).",{"type":25,"tag":37,"props":3948,"children":3950},{"id":3949},"step-5-committing-and-running-your-workflow",[3951],{"type":34,"value":3952},"Step 5: Committing and Running Your Workflow",{"type":25,"tag":30,"props":3954,"children":3955},{},[3956],{"type":34,"value":3957},"Commit your workflow file and push the changes:",{"type":25,"tag":120,"props":3959,"children":3961},{"code":3960,"language":1017,"meta":7,"className":1015,"style":7},"git add .github/workflows/maven-ci.yml\ngit commit -m \"Add Maven CI GitHub Actions workflow\"\ngit push\n",[3962],{"type":25,"tag":14,"props":3963,"children":3964},{"__ignoreMap":7},[3965,3983,4005],{"type":25,"tag":129,"props":3966,"children":3967},{"class":131,"line":132},[3968,3973,3978],{"type":25,"tag":129,"props":3969,"children":3970},{"style":153},[3971],{"type":34,"value":3972},"git",{"type":25,"tag":129,"props":3974,"children":3975},{"style":164},[3976],{"type":34,"value":3977}," add",{"type":25,"tag":129,"props":3979,"children":3980},{"style":164},[3981],{"type":34,"value":3982}," .github/workflows/maven-ci.yml\n",{"type":25,"tag":129,"props":3984,"children":3985},{"class":131,"line":175},[3986,3990,3995,4000],{"type":25,"tag":129,"props":3987,"children":3988},{"style":153},[3989],{"type":34,"value":3972},{"type":25,"tag":129,"props":3991,"children":3992},{"style":164},[3993],{"type":34,"value":3994}," commit",{"type":25,"tag":129,"props":3996,"children":3997},{"style":193},[3998],{"type":34,"value":3999}," -m",{"type":25,"tag":129,"props":4001,"children":4002},{"style":164},[4003],{"type":34,"value":4004}," \"Add Maven CI GitHub Actions workflow\"\n",{"type":25,"tag":129,"props":4006,"children":4007},{"class":131,"line":204},[4008,4012],{"type":25,"tag":129,"props":4009,"children":4010},{"style":153},[4011],{"type":34,"value":3972},{"type":25,"tag":129,"props":4013,"children":4014},{"style":164},[4015],{"type":34,"value":4016}," push\n",{"type":25,"tag":30,"props":4018,"children":4019},{},[4020,4022,4027],{"type":34,"value":4021},"Navigate to the ",{"type":25,"tag":2410,"props":4023,"children":4024},{},[4025],{"type":34,"value":4026},"Actions",{"type":34,"value":4028}," tab on your GitHub repository to view and monitor your pipeline.",{"type":25,"tag":37,"props":4030,"children":4032},{"id":4031},"advantages-of-automating-java-builds",[4033],{"type":34,"value":4034},"Advantages of Automating Java Builds",{"type":25,"tag":895,"props":4036,"children":4037},{},[4038,4043,4048,4053],{"type":25,"tag":53,"props":4039,"children":4040},{},[4041],{"type":34,"value":4042},"Rapid feedback on code integration.",{"type":25,"tag":53,"props":4044,"children":4045},{},[4046],{"type":34,"value":4047},"Early identification of bugs and issues.",{"type":25,"tag":53,"props":4049,"children":4050},{},[4051],{"type":34,"value":4052},"Automated testing and deployment.",{"type":25,"tag":53,"props":4054,"children":4055},{},[4056],{"type":34,"value":4057},"Improved reliability and consistency.",{"type":25,"tag":37,"props":4059,"children":4061},{"id":4060},"pricing",[4062],{"type":34,"value":4063},"Pricing",{"type":25,"tag":30,"props":4065,"children":4066},{},[4067],{"type":34,"value":4068},"GitHub Actions offers a generous free tier suitable for most projects:",{"type":25,"tag":895,"props":4070,"children":4071},{},[4072,4098],{"type":25,"tag":53,"props":4073,"children":4074},{},[4075,4080],{"type":25,"tag":2410,"props":4076,"children":4077},{},[4078],{"type":34,"value":4079},"Free Tier:",{"type":25,"tag":895,"props":4081,"children":4082},{},[4083,4088,4093],{"type":25,"tag":53,"props":4084,"children":4085},{},[4086],{"type":34,"value":4087},"2,000 minutes per month (private repositories).",{"type":25,"tag":53,"props":4089,"children":4090},{},[4091],{"type":34,"value":4092},"Unlimited minutes for public repositories.",{"type":25,"tag":53,"props":4094,"children":4095},{},[4096],{"type":34,"value":4097},"Free usage of GitHub-hosted runners for most common tasks.",{"type":25,"tag":53,"props":4099,"children":4100},{},[4101,4106],{"type":25,"tag":2410,"props":4102,"children":4103},{},[4104],{"type":34,"value":4105},"Additional Minutes:",{"type":25,"tag":895,"props":4107,"children":4108},{},[4109,4114,4119],{"type":25,"tag":53,"props":4110,"children":4111},{},[4112],{"type":34,"value":4113},"$0.008 per minute for Linux runners.",{"type":25,"tag":53,"props":4115,"children":4116},{},[4117],{"type":34,"value":4118},"$0.016 per minute for Windows runners.",{"type":25,"tag":53,"props":4120,"children":4121},{},[4122],{"type":34,"value":4123},"$0.08 per minute for macOS runners.",{"type":25,"tag":30,"props":4125,"children":4126},{},[4127,4129,4136],{"type":34,"value":4128},"For detailed and up-to-date pricing, visit ",{"type":25,"tag":902,"props":4130,"children":4133},{"href":4131,"rel":4132},"https://github.com/pricing#actions",[906],[4134],{"type":34,"value":4135},"GitHub Actions Pricing",{"type":34,"value":3225},{"type":25,"tag":37,"props":4138,"children":4139},{"id":878},[4140],{"type":34,"value":881},{"type":25,"tag":30,"props":4142,"children":4143},{},[4144],{"type":34,"value":4145},"Using GitHub Actions with Maven provides an efficient and robust CI/CD pipeline, significantly improving your development lifecycle. Start implementing these practices today and streamline your Java application delivery.",{"type":25,"tag":888,"props":4147,"children":4148},{"id":890},[4149],{"type":34,"value":893},{"type":25,"tag":895,"props":4151,"children":4152},{},[4153,4163,4173],{"type":25,"tag":53,"props":4154,"children":4155},{},[4156],{"type":25,"tag":902,"props":4157,"children":4160},{"href":4158,"rel":4159},"https://docs.github.com/en/actions",[906],[4161],{"type":34,"value":4162},"GitHub Actions Documentation",{"type":25,"tag":53,"props":4164,"children":4165},{},[4166],{"type":25,"tag":902,"props":4167,"children":4170},{"href":4168,"rel":4169},"https://maven.apache.org/guides/",[906],[4171],{"type":34,"value":4172},"Maven Official Documentation",{"type":25,"tag":53,"props":4174,"children":4175},{},[4176],{"type":25,"tag":902,"props":4177,"children":4180},{"href":4178,"rel":4179},"https://docs.github.com/en/packages/working-with-a-github-packages-registry",[906],[4181],{"type":34,"value":4182},"Publishing Java Packages with GitHub Packages",{"type":25,"tag":931,"props":4184,"children":4185},{},[4186],{"type":34,"value":935},{"title":7,"searchDepth":175,"depth":175,"links":4188},[4189,4190,4191,4192,4193,4194,4195,4196,4197],{"id":3228,"depth":175,"text":3231},{"id":3255,"depth":175,"text":3258},{"id":3618,"depth":175,"text":3621},{"id":3683,"depth":175,"text":3686},{"id":3854,"depth":175,"text":3857},{"id":3949,"depth":175,"text":3952},{"id":4031,"depth":175,"text":4034},{"id":4060,"depth":175,"text":4063},{"id":878,"depth":175,"text":881},"content:posts:maven-and-github-actions.md","posts/maven-and-github-actions.md","posts/maven-and-github-actions",[4202,4203,4204,4205,4206,4210,4214,4218,4222,4226,4230,4234,4238,4242,4246,4250,4254,4258,4261,4265,4269],{"_path":956,"title":957,"date":959},{"_path":4,"title":8,"date":10},{"_path":2372,"title":2373,"date":2375},{"_path":3192,"title":3193,"date":3195},{"_path":4207,"title":4208,"date":4209},"/posts/pattern-matching-sealed-classes-java21","A Guide to Pattern Matching and Sealed Classes in Java 21","2024-05-15T11:00:00.000Z",{"_path":4211,"title":4212,"date":4213},"/posts/async-java-completable-vs-reactive","Asynchronous Programming in Java: CompletableFuture vs Reactive Streams","2024-04-15T11:00:00.000Z",{"_path":4215,"title":4216,"date":4217},"/posts/mastering-concurrency","Mastering Concurrency in Java: Threads, Executors, and Virtual Threads","2024-03-15T11:00:00.000Z",{"_path":4219,"title":4220,"date":4221},"/posts/microservices-mistakes","Common Mistakes When Developing Microservices","2024-02-15T11:00:00.000Z",{"_path":4223,"title":4224,"date":4225},"/posts/tdd-testing","Test-Driven Development (TDD) in Java with JUnit and Mockito","2024-01-15T11:00:00.000Z",{"_path":4227,"title":4228,"date":4229},"/posts/single-table-design","Single Table Design","2023-12-27T11:00:00.000Z",{"_path":4231,"title":4232,"date":4233},"/posts/java-17","Exploring Java 17's New Features","2023-10-08T11:00:00.000Z",{"_path":4235,"title":4236,"date":4237},"/posts/hexagonal-architecture","Introduction to Hexagonal Architecture","2023-10-02 18:00:00",{"_path":4239,"title":4240,"date":4241},"/posts/terraform","Unleashing the Power of Infrastructure as Code (IaC)","2023-09-24 18:00:00",{"_path":4243,"title":4244,"date":4245},"/posts/python-virtual-environments","Python Virtual Environments (venv)","2023-09-17 22:00:00",{"_path":4247,"title":4248,"date":4249},"/posts/api-first-principles","API First principles","2023-09-01 22:15:18",{"_path":4251,"title":4252,"date":4253},"/posts/how-to-configure-ssh-key-based-authentication","How To Configure SSH Key-Based Authentication","2021-02-21 03:46:12",{"_path":4255,"title":4256,"date":4257},"/posts/algorithms-binary-search-tree","Algorithms - Binary Search Tree in kotlin","2020-12-06T11:00:00.000Z",{"_path":4259,"title":4260,"date":4257},"/posts/how-to-create-a-twitter-bot","How to create a Twitter bot",{"_path":4262,"title":4263,"date":4264},"/posts/manage-aws-infrastructure-with-terraform","Bootstrap complete Java application infrastructure in AWS with Terraform","2020-12-02T11:00:00.000Z",{"_path":4266,"title":4267,"date":4268},"/posts/algorithms-working-with-trees","Algorithms - Binary tree traversals in kotlin","2020-11-24T11:00:00.000Z",{"_path":4270,"title":4271,"date":4272},"/posts/playing-with-ocr-libraries","Playing with OCR libraries","2020-11-22T11:00:00.000Z",1790510065722]