Skip to content

Commit d80e627

Browse files
authored
Cache fix issues V2 (#5237)
# Description of Changes <!-- Please provide a summary of the changes, including: - What was changed - Why the change was made - Any challenges encountered Closes #(issue_number) --> --- ## Checklist ### General - [ ] I have read the [Contribution Guidelines](https://github.com/Stirling-Tools/Stirling-PDF/blob/main/CONTRIBUTING.md) - [ ] I have read the [Stirling-PDF Developer Guide](https://github.com/Stirling-Tools/Stirling-PDF/blob/main/devGuide/DeveloperGuide.md) (if applicable) - [ ] I have read the [How to add new languages to Stirling-PDF](https://github.com/Stirling-Tools/Stirling-PDF/blob/main/devGuide/HowToAddNewLanguage.md) (if applicable) - [ ] I have performed a self-review of my own code - [ ] My changes generate no new warnings ### Documentation - [ ] I have updated relevant docs on [Stirling-PDF's doc repo](https://github.com/Stirling-Tools/Stirling-Tools.github.io/blob/main/docs/) (if functionality has heavily changed) - [ ] I have read the section [Add New Translation Tags](https://github.com/Stirling-Tools/Stirling-PDF/blob/main/devGuide/HowToAddNewLanguage.md#add-new-translation-tags) (for new translation tags only) ### UI Changes (if applicable) - [ ] Screenshots or videos demonstrating the UI changes are attached (e.g., as comments or direct attachments in the PR) ### Testing (if applicable) - [ ] I have tested my changes locally. Refer to the [Testing Guide](https://github.com/Stirling-Tools/Stirling-PDF/blob/main/devGuide/DeveloperGuide.md#6-testing) for more details.
1 parent 336ec34 commit d80e627

26 files changed

Lines changed: 805 additions & 229 deletions

File tree

app/common/src/main/java/stirling/software/common/model/ApplicationProperties.java

Lines changed: 47 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,7 @@ public class ApplicationProperties {
6868

6969
private AutoPipeline autoPipeline = new AutoPipeline();
7070
private ProcessExecutor processExecutor = new ProcessExecutor();
71+
private PdfEditor pdfEditor = new PdfEditor();
7172

7273
@Bean
7374
public PropertySource<?> dynamicYamlPropertySource(ConfigurableEnvironment environment)
@@ -100,6 +101,46 @@ public static class AutoPipeline {
100101
private String outputFolder;
101102
}
102103

104+
@Data
105+
public static class PdfEditor {
106+
private Cache cache = new Cache();
107+
private FontNormalization fontNormalization = new FontNormalization();
108+
private CffConverter cffConverter = new CffConverter();
109+
private Type3 type3 = new Type3();
110+
private String fallbackFont = "classpath:/static/fonts/NotoSans-Regular.ttf";
111+
112+
@Data
113+
public static class Cache {
114+
private long maxBytes = -1;
115+
private int maxPercent = 20;
116+
}
117+
118+
@Data
119+
public static class FontNormalization {
120+
private boolean enabled = false;
121+
}
122+
123+
@Data
124+
public static class CffConverter {
125+
private boolean enabled = true;
126+
private String method = "python";
127+
private String pythonCommand = "/opt/venv/bin/python3";
128+
private String pythonScript = "/scripts/convert_cff_to_ttf.py";
129+
private String fontforgeCommand = "fontforge";
130+
}
131+
132+
@Data
133+
public static class Type3 {
134+
private Library library = new Library();
135+
136+
@Data
137+
public static class Library {
138+
private boolean enabled = true;
139+
private String index = "classpath:/type3/library/index.json";
140+
}
141+
}
142+
}
143+
103144
@Data
104145
public static class Legal {
105146
private String termsAndConditions;
@@ -368,10 +409,12 @@ public static class System {
368409
private TempFileManagement tempFileManagement = new TempFileManagement();
369410
private DatabaseBackup databaseBackup = new DatabaseBackup();
370411
private List<String> corsAllowedOrigins = new ArrayList<>();
371-
private String
372-
frontendUrl; // Base URL for frontend (used for invite links, etc.). If not set,
412+
private String backendUrl; // Backend base URL for SAML/OAuth/API callbacks (e.g.
413+
// 'http://localhost:8080', 'https://api.example.com'). Required for
414+
// SSO.
415+
private String frontendUrl; // Frontend URL for invite email links (e.g.
373416

374-
// falls back to backend URL.
417+
// 'https://app.example.com'). If not set, falls back to backendUrl.
375418

376419
public boolean isAnalyticsEnabled() {
377420
return this.getEnableAnalytics() != null && this.getEnableAnalytics();
@@ -536,6 +579,7 @@ public static class AutomaticallyGenerated {
536579
@ToString.Exclude private String key;
537580
private String UUID;
538581
private String appVersion;
582+
private Boolean isNewServer;
539583
}
540584

541585
// TODO: Remove post migration

app/core/src/main/java/stirling/software/SPDF/config/InitialSetup.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -94,6 +94,7 @@ public void initSetAppVersion() throws IOException {
9494
}
9595
GeneralUtils.saveKeyToSettings("AutomaticallyGenerated.appVersion", appVersion);
9696
applicationProperties.getAutomaticallyGenerated().setAppVersion(appVersion);
97+
applicationProperties.getAutomaticallyGenerated().setIsNewServer(isNewServer);
9798
}
9899

99100
public static boolean isNewServer() {
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
package stirling.software.SPDF.controller.api.converters;
2+
3+
import java.nio.charset.StandardCharsets;
4+
5+
import org.springframework.http.HttpStatus;
6+
import org.springframework.http.MediaType;
7+
import org.springframework.http.ResponseEntity;
8+
import org.springframework.web.bind.annotation.ControllerAdvice;
9+
import org.springframework.web.bind.annotation.ExceptionHandler;
10+
import org.springframework.web.bind.annotation.ResponseBody;
11+
12+
import com.fasterxml.jackson.databind.ObjectMapper;
13+
14+
import lombok.RequiredArgsConstructor;
15+
import lombok.extern.slf4j.Slf4j;
16+
17+
import stirling.software.SPDF.exception.CacheUnavailableException;
18+
19+
@ControllerAdvice(assignableTypes = ConvertPdfJsonController.class)
20+
@Slf4j
21+
@RequiredArgsConstructor
22+
public class ConvertPdfJsonExceptionHandler {
23+
24+
private final ObjectMapper objectMapper;
25+
26+
@ExceptionHandler(CacheUnavailableException.class)
27+
@ResponseBody
28+
public ResponseEntity<byte[]> handleCacheUnavailable(CacheUnavailableException ex) {
29+
try {
30+
byte[] body =
31+
objectMapper.writeValueAsBytes(
32+
java.util.Map.of(
33+
"error", "cache_unavailable",
34+
"action", "reupload",
35+
"message", ex.getMessage()));
36+
return ResponseEntity.status(HttpStatus.GONE)
37+
.contentType(MediaType.APPLICATION_JSON)
38+
.body(body);
39+
} catch (Exception e) {
40+
log.warn("Failed to serialize cache_unavailable response", e);
41+
var fallbackBody =
42+
java.util.Map.of(
43+
"error", "cache_unavailable",
44+
"action", "reupload",
45+
"message", String.valueOf(ex.getMessage()));
46+
try {
47+
return ResponseEntity.status(HttpStatus.GONE)
48+
.contentType(MediaType.APPLICATION_JSON)
49+
.body(objectMapper.writeValueAsBytes(fallbackBody));
50+
} catch (Exception ignored) {
51+
// Truly last-ditch fallback
52+
return ResponseEntity.status(HttpStatus.GONE)
53+
.contentType(MediaType.APPLICATION_JSON)
54+
.body(
55+
"{\"error\":\"cache_unavailable\",\"action\":\"reupload\",\"message\":\"Cache unavailable\"}"
56+
.getBytes(StandardCharsets.UTF_8));
57+
}
58+
}
59+
}
60+
}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
package stirling.software.SPDF.exception;
2+
3+
public class CacheUnavailableException extends RuntimeException {
4+
5+
public CacheUnavailableException(String message) {
6+
super(message);
7+
}
8+
}

0 commit comments

Comments
 (0)