or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

annotation-processing.mdaot-optimization.mdcore-infrastructure.mdenvironment-config.mdindex.mdresource-management.mdtask-execution.mdtype-conversion.mdutilities.md

resource-management.mddocs/

0

# Resource Management

1

2

Spring Core provides a comprehensive abstraction for accessing resources from various sources including classpath, file system, URLs, and in-memory data. This unified API simplifies resource handling across different deployment scenarios.

3

4

## Core Resource Interface

5

6

The `Resource` interface provides the fundamental abstraction for all resource types.

7

8

**Resource Interface**

9

```java { .api }

10

public interface Resource extends InputStreamSource {

11

boolean exists();

12

default boolean isReadable();

13

default boolean isOpen();

14

default boolean isFile();

15

16

URL getURL() throws IOException;

17

URI getURI() throws IOException;

18

File getFile() throws IOException;

19

default ReadableByteChannel readableChannel() throws IOException;

20

21

long contentLength() throws IOException;

22

long lastModified() throws IOException;

23

24

Resource createRelative(String relativePath) throws IOException;

25

String getFilename();

26

String getDescription();

27

28

// From InputStreamSource

29

InputStream getInputStream() throws IOException;

30

}

31

32

public interface InputStreamSource {

33

InputStream getInputStream() throws IOException;

34

}

35

```

36

37

**Writable Resource Extension**

38

```java { .api }

39

public interface WritableResource extends Resource {

40

default boolean isWritable();

41

OutputStream getOutputStream() throws IOException;

42

default WritableByteChannel writableChannel() throws IOException;

43

}

44

```

45

46

**Usage Examples**

47

```java

48

// Basic resource operations

49

Resource resource = new ClassPathResource("config/application.properties");

50

51

// Check resource existence and properties

52

if (resource.exists() && resource.isReadable()) {

53

long size = resource.contentLength();

54

long modified = resource.lastModified();

55

String filename = resource.getFilename(); // "application.properties"

56

57

// Read content

58

try (InputStream input = resource.getInputStream()) {

59

Properties props = new Properties();

60

props.load(input);

61

}

62

}

63

64

// Get file system representation

65

if (resource.isFile()) {

66

File file = resource.getFile();

67

Path path = file.toPath();

68

}

69

70

// Create relative resources

71

Resource siblingResource = resource.createRelative("../logging/logback.xml");

72

```

73

74

## Resource Implementations

75

76

Spring provides several concrete `Resource` implementations for different source types.

77

78

**ClassPath Resources**

79

```java { .api }

80

public class ClassPathResource extends AbstractFileResolvingResource {

81

public ClassPathResource(String path);

82

public ClassPathResource(String path, Class<?> clazz);

83

public ClassPathResource(String path, ClassLoader classLoader);

84

85

public final String getPath();

86

public final ClassLoader getClassLoader();

87

88

@Override

89

public boolean exists();

90

@Override

91

public InputStream getInputStream() throws IOException;

92

@Override

93

public URL getURL() throws IOException;

94

@Override

95

public String getDescription();

96

}

97

```

98

99

**File System Resources**

100

```java { .api }

101

public class FileSystemResource extends AbstractResource implements WritableResource {

102

public FileSystemResource(String path);

103

public FileSystemResource(File file);

104

public FileSystemResource(Path filePath);

105

106

public final String getPath();

107

public final File getFile();

108

109

@Override

110

public boolean exists();

111

@Override

112

public boolean isReadable();

113

@Override

114

public InputStream getInputStream() throws IOException;

115

@Override

116

public boolean isWritable();

117

@Override

118

public OutputStream getOutputStream() throws IOException;

119

@Override

120

public String getDescription();

121

}

122

```

123

124

**URL Resources**

125

```java { .api }

126

public class UrlResource extends AbstractFileResolvingResource {

127

public UrlResource(URL url);

128

public UrlResource(String location) throws MalformedURLException;

129

public UrlResource(String protocol, String location) throws MalformedURLException;

130

131

@Override

132

public InputStream getInputStream() throws IOException;

133

@Override

134

public URL getURL();

135

@Override

136

public URI getURI() throws IOException;

137

@Override

138

public boolean exists();

139

@Override

140

public String getDescription();

141

}

142

```

143

144

**Byte Array Resources**

145

```java { .api }

146

public class ByteArrayResource extends AbstractResource {

147

public ByteArrayResource(byte[] byteArray);

148

public ByteArrayResource(byte[] byteArray, String description);

149

150

public final byte[] getByteArray();

151

152

@Override

153

public boolean exists();

154

@Override

155

public long contentLength();

156

@Override

157

public InputStream getInputStream();

158

@Override

159

public String getDescription();

160

}

161

```

162

163

**Usage Examples**

164

```java

165

// ClassPath resources

166

Resource configResource = new ClassPathResource("application.yml");

167

Resource templatesDir = new ClassPathResource("templates/", MyClass.class);

168

Resource libResource = new ClassPathResource("lib/helper.jar", classLoader);

169

170

// File system resources

171

Resource dataFile = new FileSystemResource("/data/users.csv");

172

Resource tempFile = new FileSystemResource(Files.createTempFile("temp", ".txt"));

173

174

// Write to file system resource

175

if (dataFile instanceof WritableResource writable && writable.isWritable()) {

176

try (OutputStream output = writable.getOutputStream()) {

177

output.write("New data".getBytes());

178

}

179

}

180

181

// URL resources

182

Resource remoteConfig = new UrlResource("https://config.example.com/app.properties");

183

Resource jarResource = new UrlResource("jar:file:/app/lib/data.jar!/config.xml");

184

185

// Byte array resources (useful for testing)

186

byte[] data = "Test configuration".getBytes();

187

Resource memoryResource = new ByteArrayResource(data, "test-config");

188

```

189

190

## Resource Loading

191

192

Spring provides a strategy-based approach for loading resources with support for location patterns.

193

194

**ResourceLoader Interface**

195

```java { .api }

196

public interface ResourceLoader {

197

String CLASSPATH_URL_PREFIX = "classpath:";

198

199

Resource getResource(String location);

200

ClassLoader getClassLoader();

201

}

202

203

public class DefaultResourceLoader implements ResourceLoader {

204

public DefaultResourceLoader();

205

public DefaultResourceLoader(ClassLoader classLoader);

206

207

public void setClassLoader(ClassLoader classLoader);

208

209

@Override

210

public ClassLoader getClassLoader();

211

@Override

212

public Resource getResource(String location);

213

214

public void addProtocolResolver(ProtocolResolver protocolResolver);

215

public Collection<ProtocolResolver> getProtocolResolvers();

216

public void clearProtocolResolvers();

217

218

protected Resource getResourceByPath(String path);

219

}

220

```

221

222

**Pattern-Based Resource Loading**

223

```java { .api }

224

public interface ResourcePatternResolver extends ResourceLoader {

225

String CLASSPATH_ALL_URL_PREFIX = "classpath*:";

226

227

Resource[] getResources(String locationPattern) throws IOException;

228

}

229

230

public class PathMatchingResourcePatternResolver

231

implements ResourcePatternResolver, Ordered {

232

233

public PathMatchingResourcePatternResolver();

234

public PathMatchingResourcePatternResolver(ResourceLoader resourceLoader);

235

public PathMatchingResourcePatternResolver(ClassLoader classLoader);

236

237

public void setPathMatcher(PathMatcher pathMatcher);

238

public PathMatcher getPathMatcher();

239

240

@Override

241

public Resource getResource(String location);

242

@Override

243

public Resource[] getResources(String locationPattern) throws IOException;

244

245

@Override

246

public int getOrder();

247

}

248

```

249

250

**Protocol Resolver Extension**

251

```java { .api }

252

@FunctionalInterface

253

public interface ProtocolResolver {

254

Resource resolve(String location, ResourceLoader resourceLoader);

255

}

256

```

257

258

**Usage Examples**

259

```java

260

// Basic resource loading

261

ResourceLoader loader = new DefaultResourceLoader();

262

263

// Load from different sources based on prefix

264

Resource classpathResource = loader.getResource("classpath:config.properties");

265

Resource fileResource = loader.getResource("file:./data.txt");

266

Resource urlResource = loader.getResource("https://example.com/config.json");

267

268

// Pattern-based loading

269

ResourcePatternResolver resolver = new PathMatchingResourcePatternResolver();

270

271

// Load all matching resources from classpath

272

Resource[] configFiles = resolver.getResources("classpath*:config/*.properties");

273

Resource[] xmlFiles = resolver.getResources("classpath:spring/**/*.xml");

274

Resource[] allJars = resolver.getResources("classpath*:lib/*.jar");

275

276

// Process multiple resources

277

for (Resource resource : configFiles) {

278

if (resource.exists()) {

279

Properties props = new Properties();

280

try (InputStream input = resource.getInputStream()) {

281

props.load(input);

282

}

283

System.out.println("Loaded: " + resource.getDescription());

284

}

285

}

286

287

// Custom protocol resolver

288

loader.addProtocolResolver((location, resourceLoader) -> {

289

if (location.startsWith("custom:")) {

290

String path = location.substring(7);

291

return new FileSystemResource("/custom/path/" + path);

292

}

293

return null;

294

});

295

296

Resource customResource = loader.getResource("custom:myfile.txt");

297

```

298

299

## Resource Utilities

300

301

**Resource Utility Classes**

302

```java { .api }

303

public abstract class ResourceUtils {

304

public static final String CLASSPATH_URL_PREFIX = "classpath:";

305

public static final String FILE_URL_PREFIX = "file:";

306

public static final String JAR_URL_PREFIX = "jar:";

307

public static final String WAR_URL_PREFIX = "war:";

308

309

public static boolean isUrl(String resourceLocation);

310

public static URL getURL(String resourceLocation) throws FileNotFoundException;

311

public static File getFile(String resourceLocation) throws FileNotFoundException;

312

public static File getFile(URL resourceUrl) throws FileNotFoundException;

313

public static File getFile(URI resourceUri) throws FileNotFoundException;

314

315

public static boolean isFileURL(URL url);

316

public static boolean isJarURL(URL url);

317

public static boolean isJarFileURL(URL url);

318

319

public static URL extractJarFileURL(URL jarUrl) throws MalformedURLException;

320

public static URL extractArchiveURL(URL jarUrl) throws MalformedURLException;

321

322

public static URI toURI(URL url) throws URISyntaxException;

323

public static URI toURI(String location) throws URISyntaxException;

324

}

325

```

326

327

**Usage Examples**

328

```java

329

// Check resource location types

330

boolean isUrl = ResourceUtils.isUrl("https://example.com/file.txt"); // true

331

boolean isClasspath = ResourceUtils.isUrl("classpath:config.xml"); // false

332

333

// Get File objects from resource locations

334

File configFile = ResourceUtils.getFile("classpath:application.properties");

335

File dataFile = ResourceUtils.getFile("file:/data/users.csv");

336

337

// Work with JAR URLs

338

URL jarUrl = new URL("jar:file:/app/lib/mylib.jar!/config.xml");

339

boolean isJar = ResourceUtils.isJarURL(jarUrl); // true

340

URL jarFileUrl = ResourceUtils.extractJarFileURL(jarUrl); // file:/app/lib/mylib.jar

341

```

342

343

## Context Resource Interface

344

345

**Context-Aware Resources**

346

```java { .api }

347

public interface ContextResource extends Resource {

348

String getPathWithinContext();

349

}

350

351

public interface HttpResource extends Resource {

352

HttpHeaders getResponseHeaders();

353

}

354

```

355

356

**File-Based Resource Extensions**

357

```java { .api }

358

public abstract class AbstractFileResolvingResource extends AbstractResource {

359

@Override

360

public boolean exists();

361

@Override

362

public boolean isReadable();

363

@Override

364

public boolean isFile();

365

@Override

366

public File getFile() throws IOException;

367

@Override

368

public ReadableByteChannel readableChannel() throws IOException;

369

@Override

370

public long contentLength() throws IOException;

371

@Override

372

public long lastModified() throws IOException;

373

374

protected File getFileForLastModifiedCheck() throws IOException;

375

protected boolean isFile(URI uri);

376

protected File getFile(URI uri) throws IOException;

377

protected File getFile(URL url) throws IOException;

378

}

379

380

public abstract class AbstractResource implements Resource {

381

@Override

382

public boolean exists();

383

@Override

384

public boolean isReadable();

385

@Override

386

public boolean isOpen();

387

@Override

388

public boolean isFile();

389

@Override

390

public URL getURL() throws IOException;

391

@Override

392

public URI getURI() throws IOException;

393

@Override

394

public File getFile() throws IOException;

395

@Override

396

public ReadableByteChannel readableChannel() throws IOException;

397

@Override

398

public long contentLength() throws IOException;

399

@Override

400

public long lastModified() throws IOException;

401

@Override

402

public Resource createRelative(String relativePath) throws IOException;

403

@Override

404

public String getFilename();

405

406

// Utility methods

407

public String toString();

408

public boolean equals(Object other);

409

public int hashCode();

410

}

411

```

412

413

## Advanced Resource Features

414

415

**Input Stream Source Chain**

416

```java { .api }

417

public class InputStreamResource extends AbstractResource {

418

public InputStreamResource(InputStream inputStream);

419

public InputStreamResource(InputStream inputStream, String description);

420

421

@Override

422

public String getDescription();

423

@Override

424

public InputStream getInputStream() throws IOException;

425

@Override

426

public boolean equals(Object other);

427

@Override

428

public int hashCode();

429

}

430

```

431

432

**Encoded Resources**

433

```java { .api }

434

public class EncodedResource implements InputStreamSource {

435

public EncodedResource(Resource resource);

436

public EncodedResource(Resource resource, String encoding);

437

public EncodedResource(Resource resource, Charset charset);

438

439

public final Resource getResource();

440

public final String getEncoding();

441

public final Charset getCharset();

442

443

public boolean requiresReader();

444

public Reader getReader() throws IOException;

445

@Override

446

public InputStream getInputStream() throws IOException;

447

}

448

```

449

450

**Usage Examples**

451

```java

452

// Work with encoded resources

453

Resource xmlResource = new ClassPathResource("data/users.xml");

454

EncodedResource encodedXml = new EncodedResource(xmlResource, "UTF-8");

455

456

// Read as character stream

457

try (Reader reader = encodedXml.getReader()) {

458

// Parse XML with proper encoding

459

}

460

461

// Input stream resource (useful for wrapping existing streams)

462

InputStream dataStream = getDataFromSomewhere();

463

Resource streamResource = new InputStreamResource(dataStream, "external-data");

464

465

// Use in Spring configurations

466

@Bean

467

public Properties applicationProperties() throws IOException {

468

Properties props = new Properties();

469

Resource resource = new ClassPathResource("application.properties");

470

props.load(resource.getInputStream());

471

return props;

472

}

473

```

474

475

## Resource Pattern Matching

476

477

**Path Matcher Interface**

478

```java { .api }

479

public interface PathMatcher {

480

boolean isPattern(String path);

481

boolean match(String pattern, String path);

482

boolean matchStart(String pattern, String path);

483

String extractPathWithinPattern(String pattern, String path);

484

Map<String, String> extractUriTemplateVariables(String pattern, String path);

485

Comparator<String> getPatternComparator(String path);

486

String combine(String pattern1, String pattern2);

487

}

488

489

public class AntPathMatcher implements PathMatcher {

490

public static final String DEFAULT_PATH_SEPARATOR = "/";

491

492

public AntPathMatcher();

493

public AntPathMatcher(String pathSeparator);

494

495

public void setPathSeparator(String pathSeparator);

496

public void setCaseSensitive(boolean caseSensitive);

497

public void setTrimTokens(boolean trimTokens);

498

public void setCachePatterns(boolean cachePatterns);

499

500

@Override

501

public boolean isPattern(String path);

502

@Override

503

public boolean match(String pattern, String path);

504

@Override

505

public boolean matchStart(String pattern, String path);

506

@Override

507

public String extractPathWithinPattern(String pattern, String path);

508

@Override

509

public Map<String, String> extractUriTemplateVariables(String pattern, String path);

510

@Override

511

public Comparator<String> getPatternComparator(String path);

512

@Override

513

public String combine(String pattern1, String pattern2);

514

}

515

```

516

517

**Usage Examples**

518

```java

519

// Pattern matching with AntPathMatcher

520

PathMatcher matcher = new AntPathMatcher();

521

522

// Test patterns

523

boolean matches1 = matcher.match("*.txt", "readme.txt"); // true

524

boolean matches2 = matcher.match("/config/**/*.xml", "/config/prod/db.xml"); // true

525

boolean matches3 = matcher.match("/api/{version}/users", "/api/v1/users"); // true

526

527

// Extract path variables

528

Map<String, String> variables = matcher.extractUriTemplateVariables(

529

"/users/{userId}/posts/{postId}",

530

"/users/123/posts/456"

531

);

532

// Returns: {userId=123, postId=456}

533

534

// Extract path within pattern

535

String extracted = matcher.extractPathWithinPattern(

536

"/static/**",

537

"/static/css/style.css"

538

);

539

// Returns: "css/style.css"

540

541

// Combine patterns

542

String combined = matcher.combine("/api/**", "*.json"); // "/api/**/*.json"

543

```

544

545

This comprehensive resource management system provides the foundation for Spring's configuration loading, template resolution, static resource serving, and many other framework features that need to access resources from various sources in a consistent manner.