@chc880/everything-antigravity 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +54 -0
- package/assets/rules/common/coding-style.md +53 -0
- package/assets/rules/common/git-workflow.md +47 -0
- package/assets/rules/common/patterns.md +36 -0
- package/assets/rules/common/performance.md +21 -0
- package/assets/rules/common/security.md +34 -0
- package/assets/rules/common/testing.md +29 -0
- package/assets/rules/golang/coding-style.md +40 -0
- package/assets/rules/golang/patterns.md +44 -0
- package/assets/rules/golang/security.md +33 -0
- package/assets/rules/golang/testing.md +30 -0
- package/assets/rules/python/coding-style.md +52 -0
- package/assets/rules/python/patterns.md +39 -0
- package/assets/rules/python/security.md +30 -0
- package/assets/rules/python/testing.md +38 -0
- package/assets/rules/typescript/coding-style.md +44 -0
- package/assets/rules/typescript/patterns.md +50 -0
- package/assets/rules/typescript/security.md +27 -0
- package/assets/rules/typescript/testing.md +24 -0
- package/assets/skills/agent-guides/SKILL.md +40 -0
- package/assets/skills/agent-guides/references/architect.md +209 -0
- package/assets/skills/agent-guides/references/build-error-resolver.md +530 -0
- package/assets/skills/agent-guides/references/code-reviewer.md +102 -0
- package/assets/skills/agent-guides/references/database-reviewer.md +652 -0
- package/assets/skills/agent-guides/references/doc-updater.md +450 -0
- package/assets/skills/agent-guides/references/e2e-runner.md +795 -0
- package/assets/skills/agent-guides/references/go-build-resolver.md +366 -0
- package/assets/skills/agent-guides/references/go-reviewer.md +265 -0
- package/assets/skills/agent-guides/references/planner.md +117 -0
- package/assets/skills/agent-guides/references/python-reviewer.md +467 -0
- package/assets/skills/agent-guides/references/refactor-cleaner.md +304 -0
- package/assets/skills/agent-guides/references/security-reviewer.md +543 -0
- package/assets/skills/agent-guides/references/tdd-guide.md +278 -0
- package/assets/skills/backend-patterns/SKILL.md +587 -0
- package/assets/skills/clickhouse-io/SKILL.md +429 -0
- package/assets/skills/coding-standards/SKILL.md +520 -0
- package/assets/skills/cpp-testing/SKILL.md +322 -0
- package/assets/skills/django-patterns/SKILL.md +733 -0
- package/assets/skills/django-security/SKILL.md +592 -0
- package/assets/skills/django-tdd/SKILL.md +728 -0
- package/assets/skills/django-verification/SKILL.md +460 -0
- package/assets/skills/frontend-patterns/SKILL.md +631 -0
- package/assets/skills/golang-patterns/SKILL.md +673 -0
- package/assets/skills/golang-testing/SKILL.md +719 -0
- package/assets/skills/java-coding-standards/SKILL.md +138 -0
- package/assets/skills/jpa-patterns/SKILL.md +141 -0
- package/assets/skills/knowledge-management/SKILL.md +77 -0
- package/assets/skills/nutrient-document-processing/SKILL.md +165 -0
- package/assets/skills/postgres-patterns/SKILL.md +146 -0
- package/assets/skills/python-patterns/SKILL.md +749 -0
- package/assets/skills/python-testing/SKILL.md +815 -0
- package/assets/skills/security-hardening/SKILL.md +76 -0
- package/assets/skills/security-review/SKILL.md +494 -0
- package/assets/skills/security-review/cloud-infrastructure-security.md +361 -0
- package/assets/skills/springboot-patterns/SKILL.md +304 -0
- package/assets/skills/springboot-security/SKILL.md +119 -0
- package/assets/skills/springboot-tdd/SKILL.md +157 -0
- package/assets/skills/springboot-verification/SKILL.md +100 -0
- package/assets/skills/tdd-workflow/SKILL.md +409 -0
- package/assets/workflows/build-fix.md +50 -0
- package/assets/workflows/code-review.md +61 -0
- package/assets/workflows/e2e.md +65 -0
- package/assets/workflows/go-build.md +39 -0
- package/assets/workflows/go-review.md +44 -0
- package/assets/workflows/go-test.md +61 -0
- package/assets/workflows/plan.md +93 -0
- package/assets/workflows/python-review.md +95 -0
- package/assets/workflows/setup-pm.md +36 -0
- package/assets/workflows/tdd.md +75 -0
- package/assets/workflows/verify.md +81 -0
- package/bin/cli.js +69 -0
- package/lib/installer.js +301 -0
- package/package.json +34 -0
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: java-coding-standards
|
|
3
|
+
description: Java coding standards for Spring Boot services: naming, immutability, Optional usage, streams, exceptions, generics, and project layout.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Java Coding Standards
|
|
7
|
+
|
|
8
|
+
Standards for readable, maintainable Java (17+) code in Spring Boot services.
|
|
9
|
+
|
|
10
|
+
## Core Principles
|
|
11
|
+
|
|
12
|
+
- Prefer clarity over cleverness
|
|
13
|
+
- Immutable by default; minimize shared mutable state
|
|
14
|
+
- Fail fast with meaningful exceptions
|
|
15
|
+
- Consistent naming and package structure
|
|
16
|
+
|
|
17
|
+
## Naming
|
|
18
|
+
|
|
19
|
+
```java
|
|
20
|
+
// ✅ Classes/Records: PascalCase
|
|
21
|
+
public class MarketService {}
|
|
22
|
+
public record Money(BigDecimal amount, Currency currency) {}
|
|
23
|
+
|
|
24
|
+
// ✅ Methods/fields: camelCase
|
|
25
|
+
private final MarketRepository marketRepository;
|
|
26
|
+
public Market findBySlug(String slug) {}
|
|
27
|
+
|
|
28
|
+
// ✅ Constants: UPPER_SNAKE_CASE
|
|
29
|
+
private static final int MAX_PAGE_SIZE = 100;
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
## Immutability
|
|
33
|
+
|
|
34
|
+
```java
|
|
35
|
+
// ✅ Favor records and final fields
|
|
36
|
+
public record MarketDto(Long id, String name, MarketStatus status) {}
|
|
37
|
+
|
|
38
|
+
public class Market {
|
|
39
|
+
private final Long id;
|
|
40
|
+
private final String name;
|
|
41
|
+
// getters only, no setters
|
|
42
|
+
}
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
## Optional Usage
|
|
46
|
+
|
|
47
|
+
```java
|
|
48
|
+
// ✅ Return Optional from find* methods
|
|
49
|
+
Optional<Market> market = marketRepository.findBySlug(slug);
|
|
50
|
+
|
|
51
|
+
// ✅ Map/flatMap instead of get()
|
|
52
|
+
return market
|
|
53
|
+
.map(MarketResponse::from)
|
|
54
|
+
.orElseThrow(() -> new EntityNotFoundException("Market not found"));
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
## Streams Best Practices
|
|
58
|
+
|
|
59
|
+
```java
|
|
60
|
+
// ✅ Use streams for transformations, keep pipelines short
|
|
61
|
+
List<String> names = markets.stream()
|
|
62
|
+
.map(Market::name)
|
|
63
|
+
.filter(Objects::nonNull)
|
|
64
|
+
.toList();
|
|
65
|
+
|
|
66
|
+
// ❌ Avoid complex nested streams; prefer loops for clarity
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
## Exceptions
|
|
70
|
+
|
|
71
|
+
- Use unchecked exceptions for domain errors; wrap technical exceptions with context
|
|
72
|
+
- Create domain-specific exceptions (e.g., `MarketNotFoundException`)
|
|
73
|
+
- Avoid broad `catch (Exception ex)` unless rethrowing/logging centrally
|
|
74
|
+
|
|
75
|
+
```java
|
|
76
|
+
throw new MarketNotFoundException(slug);
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
## Generics and Type Safety
|
|
80
|
+
|
|
81
|
+
- Avoid raw types; declare generic parameters
|
|
82
|
+
- Prefer bounded generics for reusable utilities
|
|
83
|
+
|
|
84
|
+
```java
|
|
85
|
+
public <T extends Identifiable> Map<Long, T> indexById(Collection<T> items) { ... }
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
## Project Structure (Maven/Gradle)
|
|
89
|
+
|
|
90
|
+
```
|
|
91
|
+
src/main/java/com/example/app/
|
|
92
|
+
config/
|
|
93
|
+
controller/
|
|
94
|
+
service/
|
|
95
|
+
repository/
|
|
96
|
+
domain/
|
|
97
|
+
dto/
|
|
98
|
+
util/
|
|
99
|
+
src/main/resources/
|
|
100
|
+
application.yml
|
|
101
|
+
src/test/java/... (mirrors main)
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
## Formatting and Style
|
|
105
|
+
|
|
106
|
+
- Use 2 or 4 spaces consistently (project standard)
|
|
107
|
+
- One public top-level type per file
|
|
108
|
+
- Keep methods short and focused; extract helpers
|
|
109
|
+
- Order members: constants, fields, constructors, public methods, protected, private
|
|
110
|
+
|
|
111
|
+
## Code Smells to Avoid
|
|
112
|
+
|
|
113
|
+
- Long parameter lists → use DTO/builders
|
|
114
|
+
- Deep nesting → early returns
|
|
115
|
+
- Magic numbers → named constants
|
|
116
|
+
- Static mutable state → prefer dependency injection
|
|
117
|
+
- Silent catch blocks → log and act or rethrow
|
|
118
|
+
|
|
119
|
+
## Logging
|
|
120
|
+
|
|
121
|
+
```java
|
|
122
|
+
private static final Logger log = LoggerFactory.getLogger(MarketService.class);
|
|
123
|
+
log.info("fetch_market slug={}", slug);
|
|
124
|
+
log.error("failed_fetch_market slug={}", slug, ex);
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
## Null Handling
|
|
128
|
+
|
|
129
|
+
- Accept `@Nullable` only when unavoidable; otherwise use `@NonNull`
|
|
130
|
+
- Use Bean Validation (`@NotNull`, `@NotBlank`) on inputs
|
|
131
|
+
|
|
132
|
+
## Testing Expectations
|
|
133
|
+
|
|
134
|
+
- JUnit 5 + AssertJ for fluent assertions
|
|
135
|
+
- Mockito for mocking; avoid partial mocks where possible
|
|
136
|
+
- Favor deterministic tests; no hidden sleeps
|
|
137
|
+
|
|
138
|
+
**Remember**: Keep code intentional, typed, and observable. Optimize for maintainability over micro-optimizations unless proven necessary.
|
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: jpa-patterns
|
|
3
|
+
description: JPA/Hibernate patterns for entity design, relationships, query optimization, transactions, auditing, indexing, pagination, and pooling in Spring Boot.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# JPA/Hibernate Patterns
|
|
7
|
+
|
|
8
|
+
Use for data modeling, repositories, and performance tuning in Spring Boot.
|
|
9
|
+
|
|
10
|
+
## Entity Design
|
|
11
|
+
|
|
12
|
+
```java
|
|
13
|
+
@Entity
|
|
14
|
+
@Table(name = "markets", indexes = {
|
|
15
|
+
@Index(name = "idx_markets_slug", columnList = "slug", unique = true)
|
|
16
|
+
})
|
|
17
|
+
@EntityListeners(AuditingEntityListener.class)
|
|
18
|
+
public class MarketEntity {
|
|
19
|
+
@Id @GeneratedValue(strategy = GenerationType.IDENTITY)
|
|
20
|
+
private Long id;
|
|
21
|
+
|
|
22
|
+
@Column(nullable = false, length = 200)
|
|
23
|
+
private String name;
|
|
24
|
+
|
|
25
|
+
@Column(nullable = false, unique = true, length = 120)
|
|
26
|
+
private String slug;
|
|
27
|
+
|
|
28
|
+
@Enumerated(EnumType.STRING)
|
|
29
|
+
private MarketStatus status = MarketStatus.ACTIVE;
|
|
30
|
+
|
|
31
|
+
@CreatedDate private Instant createdAt;
|
|
32
|
+
@LastModifiedDate private Instant updatedAt;
|
|
33
|
+
}
|
|
34
|
+
```
|
|
35
|
+
|
|
36
|
+
Enable auditing:
|
|
37
|
+
```java
|
|
38
|
+
@Configuration
|
|
39
|
+
@EnableJpaAuditing
|
|
40
|
+
class JpaConfig {}
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
## Relationships and N+1 Prevention
|
|
44
|
+
|
|
45
|
+
```java
|
|
46
|
+
@OneToMany(mappedBy = "market", cascade = CascadeType.ALL, orphanRemoval = true)
|
|
47
|
+
private List<PositionEntity> positions = new ArrayList<>();
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
- Default to lazy loading; use `JOIN FETCH` in queries when needed
|
|
51
|
+
- Avoid `EAGER` on collections; use DTO projections for read paths
|
|
52
|
+
|
|
53
|
+
```java
|
|
54
|
+
@Query("select m from MarketEntity m left join fetch m.positions where m.id = :id")
|
|
55
|
+
Optional<MarketEntity> findWithPositions(@Param("id") Long id);
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
## Repository Patterns
|
|
59
|
+
|
|
60
|
+
```java
|
|
61
|
+
public interface MarketRepository extends JpaRepository<MarketEntity, Long> {
|
|
62
|
+
Optional<MarketEntity> findBySlug(String slug);
|
|
63
|
+
|
|
64
|
+
@Query("select m from MarketEntity m where m.status = :status")
|
|
65
|
+
Page<MarketEntity> findByStatus(@Param("status") MarketStatus status, Pageable pageable);
|
|
66
|
+
}
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
- Use projections for lightweight queries:
|
|
70
|
+
```java
|
|
71
|
+
public interface MarketSummary {
|
|
72
|
+
Long getId();
|
|
73
|
+
String getName();
|
|
74
|
+
MarketStatus getStatus();
|
|
75
|
+
}
|
|
76
|
+
Page<MarketSummary> findAllBy(Pageable pageable);
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
## Transactions
|
|
80
|
+
|
|
81
|
+
- Annotate service methods with `@Transactional`
|
|
82
|
+
- Use `@Transactional(readOnly = true)` for read paths to optimize
|
|
83
|
+
- Choose propagation carefully; avoid long-running transactions
|
|
84
|
+
|
|
85
|
+
```java
|
|
86
|
+
@Transactional
|
|
87
|
+
public Market updateStatus(Long id, MarketStatus status) {
|
|
88
|
+
MarketEntity entity = repo.findById(id)
|
|
89
|
+
.orElseThrow(() -> new EntityNotFoundException("Market"));
|
|
90
|
+
entity.setStatus(status);
|
|
91
|
+
return Market.from(entity);
|
|
92
|
+
}
|
|
93
|
+
```
|
|
94
|
+
|
|
95
|
+
## Pagination
|
|
96
|
+
|
|
97
|
+
```java
|
|
98
|
+
PageRequest page = PageRequest.of(pageNumber, pageSize, Sort.by("createdAt").descending());
|
|
99
|
+
Page<MarketEntity> markets = repo.findByStatus(MarketStatus.ACTIVE, page);
|
|
100
|
+
```
|
|
101
|
+
|
|
102
|
+
For cursor-like pagination, include `id > :lastId` in JPQL with ordering.
|
|
103
|
+
|
|
104
|
+
## Indexing and Performance
|
|
105
|
+
|
|
106
|
+
- Add indexes for common filters (`status`, `slug`, foreign keys)
|
|
107
|
+
- Use composite indexes matching query patterns (`status, created_at`)
|
|
108
|
+
- Avoid `select *`; project only needed columns
|
|
109
|
+
- Batch writes with `saveAll` and `hibernate.jdbc.batch_size`
|
|
110
|
+
|
|
111
|
+
## Connection Pooling (HikariCP)
|
|
112
|
+
|
|
113
|
+
Recommended properties:
|
|
114
|
+
```
|
|
115
|
+
spring.datasource.hikari.maximum-pool-size=20
|
|
116
|
+
spring.datasource.hikari.minimum-idle=5
|
|
117
|
+
spring.datasource.hikari.connection-timeout=30000
|
|
118
|
+
spring.datasource.hikari.validation-timeout=5000
|
|
119
|
+
```
|
|
120
|
+
|
|
121
|
+
For PostgreSQL LOB handling, add:
|
|
122
|
+
```
|
|
123
|
+
spring.jpa.properties.hibernate.jdbc.lob.non_contextual_creation=true
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
## Caching
|
|
127
|
+
|
|
128
|
+
- 1st-level cache is per EntityManager; avoid keeping entities across transactions
|
|
129
|
+
- For read-heavy entities, consider second-level cache cautiously; validate eviction strategy
|
|
130
|
+
|
|
131
|
+
## Migrations
|
|
132
|
+
|
|
133
|
+
- Use Flyway or Liquibase; never rely on Hibernate auto DDL in production
|
|
134
|
+
- Keep migrations idempotent and additive; avoid dropping columns without plan
|
|
135
|
+
|
|
136
|
+
## Testing Data Access
|
|
137
|
+
|
|
138
|
+
- Prefer `@DataJpaTest` with Testcontainers to mirror production
|
|
139
|
+
- Assert SQL efficiency using logs: set `logging.level.org.hibernate.SQL=DEBUG` and `logging.level.org.hibernate.orm.jdbc.bind=TRACE` for parameter values
|
|
140
|
+
|
|
141
|
+
**Remember**: Keep entities lean, queries intentional, and transactions short. Prevent N+1 with fetch strategies and projections, and index for your read/write paths.
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: knowledge-management
|
|
3
|
+
description: 利用 Antigravity Knowledge Items (KI) 系统进行项目知识管理和持续学习。当需要沉淀知识、记录架构决策或在会话间传递上下文时激活。
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Knowledge Management — 项目知识沉淀指南
|
|
7
|
+
|
|
8
|
+
Antigravity 的 Knowledge Items (KI) 是跨会话持久记忆系统,能自动从对话中蒸馏关键知识。本 Skill 指导如何有效利用这一系统实现项目的持续学习。
|
|
9
|
+
|
|
10
|
+
## 何时应该沉淀知识
|
|
11
|
+
|
|
12
|
+
以下场景应主动整理和标注关键信息,以便 KI 系统捕获:
|
|
13
|
+
|
|
14
|
+
### 高价值知识类型
|
|
15
|
+
|
|
16
|
+
| 类型 | 示例 | 价值 |
|
|
17
|
+
|---|---|---|
|
|
18
|
+
| **架构决策** | 为什么选 PostgreSQL 而不是 MongoDB | 避免重复讨论 |
|
|
19
|
+
| **Bug 修复模式** | 某类 race condition 的通用解法 | 避免重复踩坑 |
|
|
20
|
+
| **项目约定** | API 命名规范、目录结构约定 | 保持一致性 |
|
|
21
|
+
| **环境配置** | Docker compose 配置、环境变量说明 | 快速上手 |
|
|
22
|
+
| **性能优化** | 查询优化、缓存策略 | 知识复用 |
|
|
23
|
+
| **安全规则** | 认证流程、密钥管理方式 | 安全合规 |
|
|
24
|
+
|
|
25
|
+
### 低价值知识(不需要沉淀)
|
|
26
|
+
|
|
27
|
+
- 一次性的语法问题
|
|
28
|
+
- 简单的 CRUD 代码
|
|
29
|
+
- 临时调试信息
|
|
30
|
+
|
|
31
|
+
## 如何让 KI 更有效
|
|
32
|
+
|
|
33
|
+
### 1. 清晰表述决策理由
|
|
34
|
+
|
|
35
|
+
```
|
|
36
|
+
不好:用了 Redis 做缓存。
|
|
37
|
+
好: 选择 Redis 做会话缓存,原因:1) 支持 TTL 自动过期 2) 集群支持 3) 团队已有运维经验。
|
|
38
|
+
备选方案 Memcached 因不支持持久化而放弃。
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
### 2. 结构化技术方案
|
|
42
|
+
|
|
43
|
+
在讨论架构时,使用结构化格式帮助 KI 系统更好地提取:
|
|
44
|
+
|
|
45
|
+
```markdown
|
|
46
|
+
## 决策:[主题]
|
|
47
|
+
- **背景**: 为什么需要做这个决策
|
|
48
|
+
- **方案**: 选择了什么
|
|
49
|
+
- **理由**: 为什么选这个
|
|
50
|
+
- **备选**: 考虑过但放弃的方案
|
|
51
|
+
- **影响**: 这个决策影响哪些组件
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
### 3. 标注关键约定
|
|
55
|
+
|
|
56
|
+
项目级别的约定应该明确表述:
|
|
57
|
+
|
|
58
|
+
```markdown
|
|
59
|
+
## 项目约定
|
|
60
|
+
- API 路径格式: `/api/v1/{resource}/{id}`
|
|
61
|
+
- 错误响应: 统一使用 `{ error: string, code: number }`
|
|
62
|
+
- 数据库迁移: 使用 Prisma Migrate,禁止手动修改
|
|
63
|
+
```
|
|
64
|
+
|
|
65
|
+
## 在新对话中利用 KI
|
|
66
|
+
|
|
67
|
+
每次新对话开始时,Antigravity 会自动提供相关 KI 摘要。正确的做法:
|
|
68
|
+
|
|
69
|
+
1. **先查 KI 摘要**,看是否已有相关知识
|
|
70
|
+
2. **引用已有 KI**,避免重复研究
|
|
71
|
+
3. **补充更新**,如果现有 KI 信息已过时
|
|
72
|
+
|
|
73
|
+
## 反模式
|
|
74
|
+
|
|
75
|
+
❌ 不要在每次对话中从头解释项目架构
|
|
76
|
+
❌ 不要忽略 KI 摘要直接开始工作
|
|
77
|
+
❌ 不要让关键决策只存在于口头沟通中
|
|
@@ -0,0 +1,165 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: nutrient-document-processing
|
|
3
|
+
description: Process, convert, OCR, extract, redact, sign, and fill documents using the Nutrient DWS API. Works with PDFs, DOCX, XLSX, PPTX, HTML, and images.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Nutrient Document Processing
|
|
7
|
+
|
|
8
|
+
Process documents with the [Nutrient DWS Processor API](https://www.nutrient.io/api/). Convert formats, extract text and tables, OCR scanned documents, redact PII, add watermarks, digitally sign, and fill PDF forms.
|
|
9
|
+
|
|
10
|
+
## Setup
|
|
11
|
+
|
|
12
|
+
Get a free API key at **[nutrient.io](https://dashboard.nutrient.io/sign_up/?product=processor)**
|
|
13
|
+
|
|
14
|
+
```bash
|
|
15
|
+
export NUTRIENT_API_KEY="pdf_live_..."
|
|
16
|
+
```
|
|
17
|
+
|
|
18
|
+
All requests go to `https://api.nutrient.io/build` as multipart POST with an `instructions` JSON field.
|
|
19
|
+
|
|
20
|
+
## Operations
|
|
21
|
+
|
|
22
|
+
### Convert Documents
|
|
23
|
+
|
|
24
|
+
```bash
|
|
25
|
+
# DOCX to PDF
|
|
26
|
+
curl -X POST https://api.nutrient.io/build \
|
|
27
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
28
|
+
-F "document.docx=@document.docx" \
|
|
29
|
+
-F 'instructions={"parts":[{"file":"document.docx"}]}' \
|
|
30
|
+
-o output.pdf
|
|
31
|
+
|
|
32
|
+
# PDF to DOCX
|
|
33
|
+
curl -X POST https://api.nutrient.io/build \
|
|
34
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
35
|
+
-F "document.pdf=@document.pdf" \
|
|
36
|
+
-F 'instructions={"parts":[{"file":"document.pdf"}],"output":{"type":"docx"}}' \
|
|
37
|
+
-o output.docx
|
|
38
|
+
|
|
39
|
+
# HTML to PDF
|
|
40
|
+
curl -X POST https://api.nutrient.io/build \
|
|
41
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
42
|
+
-F "index.html=@index.html" \
|
|
43
|
+
-F 'instructions={"parts":[{"html":"index.html"}]}' \
|
|
44
|
+
-o output.pdf
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
Supported inputs: PDF, DOCX, XLSX, PPTX, DOC, XLS, PPT, PPS, PPSX, ODT, RTF, HTML, JPG, PNG, TIFF, HEIC, GIF, WebP, SVG, TGA, EPS.
|
|
48
|
+
|
|
49
|
+
### Extract Text and Data
|
|
50
|
+
|
|
51
|
+
```bash
|
|
52
|
+
# Extract plain text
|
|
53
|
+
curl -X POST https://api.nutrient.io/build \
|
|
54
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
55
|
+
-F "document.pdf=@document.pdf" \
|
|
56
|
+
-F 'instructions={"parts":[{"file":"document.pdf"}],"output":{"type":"text"}}' \
|
|
57
|
+
-o output.txt
|
|
58
|
+
|
|
59
|
+
# Extract tables as Excel
|
|
60
|
+
curl -X POST https://api.nutrient.io/build \
|
|
61
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
62
|
+
-F "document.pdf=@document.pdf" \
|
|
63
|
+
-F 'instructions={"parts":[{"file":"document.pdf"}],"output":{"type":"xlsx"}}' \
|
|
64
|
+
-o tables.xlsx
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
### OCR Scanned Documents
|
|
68
|
+
|
|
69
|
+
```bash
|
|
70
|
+
# OCR to searchable PDF (supports 100+ languages)
|
|
71
|
+
curl -X POST https://api.nutrient.io/build \
|
|
72
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
73
|
+
-F "scanned.pdf=@scanned.pdf" \
|
|
74
|
+
-F 'instructions={"parts":[{"file":"scanned.pdf"}],"actions":[{"type":"ocr","language":"english"}]}' \
|
|
75
|
+
-o searchable.pdf
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
Languages: Supports 100+ languages via ISO 639-2 codes (e.g., `eng`, `deu`, `fra`, `spa`, `jpn`, `kor`, `chi_sim`, `chi_tra`, `ara`, `hin`, `rus`). Full language names like `english` or `german` also work. See the [complete OCR language table](https://www.nutrient.io/guides/document-engine/ocr/language-support/) for all supported codes.
|
|
79
|
+
|
|
80
|
+
### Redact Sensitive Information
|
|
81
|
+
|
|
82
|
+
```bash
|
|
83
|
+
# Pattern-based (SSN, email)
|
|
84
|
+
curl -X POST https://api.nutrient.io/build \
|
|
85
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
86
|
+
-F "document.pdf=@document.pdf" \
|
|
87
|
+
-F 'instructions={"parts":[{"file":"document.pdf"}],"actions":[{"type":"redaction","strategy":"preset","strategyOptions":{"preset":"social-security-number"}},{"type":"redaction","strategy":"preset","strategyOptions":{"preset":"email-address"}}]}' \
|
|
88
|
+
-o redacted.pdf
|
|
89
|
+
|
|
90
|
+
# Regex-based
|
|
91
|
+
curl -X POST https://api.nutrient.io/build \
|
|
92
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
93
|
+
-F "document.pdf=@document.pdf" \
|
|
94
|
+
-F 'instructions={"parts":[{"file":"document.pdf"}],"actions":[{"type":"redaction","strategy":"regex","strategyOptions":{"regex":"\\b[A-Z]{2}\\d{6}\\b"}}]}' \
|
|
95
|
+
-o redacted.pdf
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
Presets: `social-security-number`, `email-address`, `credit-card-number`, `international-phone-number`, `north-american-phone-number`, `date`, `time`, `url`, `ipv4`, `ipv6`, `mac-address`, `us-zip-code`, `vin`.
|
|
99
|
+
|
|
100
|
+
### Add Watermarks
|
|
101
|
+
|
|
102
|
+
```bash
|
|
103
|
+
curl -X POST https://api.nutrient.io/build \
|
|
104
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
105
|
+
-F "document.pdf=@document.pdf" \
|
|
106
|
+
-F 'instructions={"parts":[{"file":"document.pdf"}],"actions":[{"type":"watermark","text":"CONFIDENTIAL","fontSize":72,"opacity":0.3,"rotation":-45}]}' \
|
|
107
|
+
-o watermarked.pdf
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
### Digital Signatures
|
|
111
|
+
|
|
112
|
+
```bash
|
|
113
|
+
# Self-signed CMS signature
|
|
114
|
+
curl -X POST https://api.nutrient.io/build \
|
|
115
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
116
|
+
-F "document.pdf=@document.pdf" \
|
|
117
|
+
-F 'instructions={"parts":[{"file":"document.pdf"}],"actions":[{"type":"sign","signatureType":"cms"}]}' \
|
|
118
|
+
-o signed.pdf
|
|
119
|
+
```
|
|
120
|
+
|
|
121
|
+
### Fill PDF Forms
|
|
122
|
+
|
|
123
|
+
```bash
|
|
124
|
+
curl -X POST https://api.nutrient.io/build \
|
|
125
|
+
-H "Authorization: Bearer $NUTRIENT_API_KEY" \
|
|
126
|
+
-F "form.pdf=@form.pdf" \
|
|
127
|
+
-F 'instructions={"parts":[{"file":"form.pdf"}],"actions":[{"type":"fillForm","formFields":{"name":"Jane Smith","email":"jane@example.com","date":"2026-02-06"}}]}' \
|
|
128
|
+
-o filled.pdf
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
## MCP Server (Alternative)
|
|
132
|
+
|
|
133
|
+
For native tool integration, use the MCP server instead of curl:
|
|
134
|
+
|
|
135
|
+
```json
|
|
136
|
+
{
|
|
137
|
+
"mcpServers": {
|
|
138
|
+
"nutrient-dws": {
|
|
139
|
+
"command": "npx",
|
|
140
|
+
"args": ["-y", "@nutrient-sdk/dws-mcp-server"],
|
|
141
|
+
"env": {
|
|
142
|
+
"NUTRIENT_DWS_API_KEY": "YOUR_API_KEY",
|
|
143
|
+
"SANDBOX_PATH": "/path/to/working/directory"
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
```
|
|
149
|
+
|
|
150
|
+
## When to Use
|
|
151
|
+
|
|
152
|
+
- Converting documents between formats (PDF, DOCX, XLSX, PPTX, HTML, images)
|
|
153
|
+
- Extracting text, tables, or key-value pairs from PDFs
|
|
154
|
+
- OCR on scanned documents or images
|
|
155
|
+
- Redacting PII before sharing documents
|
|
156
|
+
- Adding watermarks to drafts or confidential documents
|
|
157
|
+
- Digitally signing contracts or agreements
|
|
158
|
+
- Filling PDF forms programmatically
|
|
159
|
+
|
|
160
|
+
## Links
|
|
161
|
+
|
|
162
|
+
- [API Playground](https://dashboard.nutrient.io/processor-api/playground/)
|
|
163
|
+
- [Full API Docs](https://www.nutrient.io/guides/dws-processor/)
|
|
164
|
+
- [Agent Skill Repo](https://github.com/PSPDFKit-labs/nutrient-agent-skill)
|
|
165
|
+
- [npm MCP Server](https://www.npmjs.com/package/@nutrient-sdk/dws-mcp-server)
|
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: postgres-patterns
|
|
3
|
+
description: PostgreSQL database patterns for query optimization, schema design, indexing, and security. Based on Supabase best practices.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# PostgreSQL Patterns
|
|
7
|
+
|
|
8
|
+
Quick reference for PostgreSQL best practices. For detailed guidance, use the `database-reviewer` agent.
|
|
9
|
+
|
|
10
|
+
## When to Activate
|
|
11
|
+
|
|
12
|
+
- Writing SQL queries or migrations
|
|
13
|
+
- Designing database schemas
|
|
14
|
+
- Troubleshooting slow queries
|
|
15
|
+
- Implementing Row Level Security
|
|
16
|
+
- Setting up connection pooling
|
|
17
|
+
|
|
18
|
+
## Quick Reference
|
|
19
|
+
|
|
20
|
+
### Index Cheat Sheet
|
|
21
|
+
|
|
22
|
+
| Query Pattern | Index Type | Example |
|
|
23
|
+
|--------------|------------|---------|
|
|
24
|
+
| `WHERE col = value` | B-tree (default) | `CREATE INDEX idx ON t (col)` |
|
|
25
|
+
| `WHERE col > value` | B-tree | `CREATE INDEX idx ON t (col)` |
|
|
26
|
+
| `WHERE a = x AND b > y` | Composite | `CREATE INDEX idx ON t (a, b)` |
|
|
27
|
+
| `WHERE jsonb @> '{}'` | GIN | `CREATE INDEX idx ON t USING gin (col)` |
|
|
28
|
+
| `WHERE tsv @@ query` | GIN | `CREATE INDEX idx ON t USING gin (col)` |
|
|
29
|
+
| Time-series ranges | BRIN | `CREATE INDEX idx ON t USING brin (col)` |
|
|
30
|
+
|
|
31
|
+
### Data Type Quick Reference
|
|
32
|
+
|
|
33
|
+
| Use Case | Correct Type | Avoid |
|
|
34
|
+
|----------|-------------|-------|
|
|
35
|
+
| IDs | `bigint` | `int`, random UUID |
|
|
36
|
+
| Strings | `text` | `varchar(255)` |
|
|
37
|
+
| Timestamps | `timestamptz` | `timestamp` |
|
|
38
|
+
| Money | `numeric(10,2)` | `float` |
|
|
39
|
+
| Flags | `boolean` | `varchar`, `int` |
|
|
40
|
+
|
|
41
|
+
### Common Patterns
|
|
42
|
+
|
|
43
|
+
**Composite Index Order:**
|
|
44
|
+
```sql
|
|
45
|
+
-- Equality columns first, then range columns
|
|
46
|
+
CREATE INDEX idx ON orders (status, created_at);
|
|
47
|
+
-- Works for: WHERE status = 'pending' AND created_at > '2024-01-01'
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
**Covering Index:**
|
|
51
|
+
```sql
|
|
52
|
+
CREATE INDEX idx ON users (email) INCLUDE (name, created_at);
|
|
53
|
+
-- Avoids table lookup for SELECT email, name, created_at
|
|
54
|
+
```
|
|
55
|
+
|
|
56
|
+
**Partial Index:**
|
|
57
|
+
```sql
|
|
58
|
+
CREATE INDEX idx ON users (email) WHERE deleted_at IS NULL;
|
|
59
|
+
-- Smaller index, only includes active users
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
**RLS Policy (Optimized):**
|
|
63
|
+
```sql
|
|
64
|
+
CREATE POLICY policy ON orders
|
|
65
|
+
USING ((SELECT auth.uid()) = user_id); -- Wrap in SELECT!
|
|
66
|
+
```
|
|
67
|
+
|
|
68
|
+
**UPSERT:**
|
|
69
|
+
```sql
|
|
70
|
+
INSERT INTO settings (user_id, key, value)
|
|
71
|
+
VALUES (123, 'theme', 'dark')
|
|
72
|
+
ON CONFLICT (user_id, key)
|
|
73
|
+
DO UPDATE SET value = EXCLUDED.value;
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
**Cursor Pagination:**
|
|
77
|
+
```sql
|
|
78
|
+
SELECT * FROM products WHERE id > $last_id ORDER BY id LIMIT 20;
|
|
79
|
+
-- O(1) vs OFFSET which is O(n)
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
**Queue Processing:**
|
|
83
|
+
```sql
|
|
84
|
+
UPDATE jobs SET status = 'processing'
|
|
85
|
+
WHERE id = (
|
|
86
|
+
SELECT id FROM jobs WHERE status = 'pending'
|
|
87
|
+
ORDER BY created_at LIMIT 1
|
|
88
|
+
FOR UPDATE SKIP LOCKED
|
|
89
|
+
) RETURNING *;
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
### Anti-Pattern Detection
|
|
93
|
+
|
|
94
|
+
```sql
|
|
95
|
+
-- Find unindexed foreign keys
|
|
96
|
+
SELECT conrelid::regclass, a.attname
|
|
97
|
+
FROM pg_constraint c
|
|
98
|
+
JOIN pg_attribute a ON a.attrelid = c.conrelid AND a.attnum = ANY(c.conkey)
|
|
99
|
+
WHERE c.contype = 'f'
|
|
100
|
+
AND NOT EXISTS (
|
|
101
|
+
SELECT 1 FROM pg_index i
|
|
102
|
+
WHERE i.indrelid = c.conrelid AND a.attnum = ANY(i.indkey)
|
|
103
|
+
);
|
|
104
|
+
|
|
105
|
+
-- Find slow queries
|
|
106
|
+
SELECT query, mean_exec_time, calls
|
|
107
|
+
FROM pg_stat_statements
|
|
108
|
+
WHERE mean_exec_time > 100
|
|
109
|
+
ORDER BY mean_exec_time DESC;
|
|
110
|
+
|
|
111
|
+
-- Check table bloat
|
|
112
|
+
SELECT relname, n_dead_tup, last_vacuum
|
|
113
|
+
FROM pg_stat_user_tables
|
|
114
|
+
WHERE n_dead_tup > 1000
|
|
115
|
+
ORDER BY n_dead_tup DESC;
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
### Configuration Template
|
|
119
|
+
|
|
120
|
+
```sql
|
|
121
|
+
-- Connection limits (adjust for RAM)
|
|
122
|
+
ALTER SYSTEM SET max_connections = 100;
|
|
123
|
+
ALTER SYSTEM SET work_mem = '8MB';
|
|
124
|
+
|
|
125
|
+
-- Timeouts
|
|
126
|
+
ALTER SYSTEM SET idle_in_transaction_session_timeout = '30s';
|
|
127
|
+
ALTER SYSTEM SET statement_timeout = '30s';
|
|
128
|
+
|
|
129
|
+
-- Monitoring
|
|
130
|
+
CREATE EXTENSION IF NOT EXISTS pg_stat_statements;
|
|
131
|
+
|
|
132
|
+
-- Security defaults
|
|
133
|
+
REVOKE ALL ON SCHEMA public FROM public;
|
|
134
|
+
|
|
135
|
+
SELECT pg_reload_conf();
|
|
136
|
+
```
|
|
137
|
+
|
|
138
|
+
## Related
|
|
139
|
+
|
|
140
|
+
- Agent: `database-reviewer` - Full database review workflow
|
|
141
|
+
- Skill: `clickhouse-io` - ClickHouse analytics patterns
|
|
142
|
+
- Skill: `backend-patterns` - API and backend patterns
|
|
143
|
+
|
|
144
|
+
---
|
|
145
|
+
|
|
146
|
+
*Based on [Supabase Agent Skills](https://github.com/supabase/agent-skills) (MIT License)*
|