alunduil / alunduil/siren-json.hs

The ToJSON instances share one omit-empty helper

未關閉
#162 0 則留言 0 個 reaction 已指派 0 人 在 GitHub 檢視
enhancement
主要語言
Haskell
星號
3
分支
1
平均合併
5 小時 46 分鐘
30 天內合併 PR
63

描述

## Summary

The four `ToJSON` instances drop empty collections through one helper rather
than repeating the same conditional eight times.

## Motivation

Siren draws no distinction between an absent array and an empty one, so every
optional collection is omitted from the encoding. That rule is currently spelled
out at each field:

```haskell
[ if null eClass then Nothing else Just $ "class" .= eClass
, if Map.null eProperties then Nothing else Just $ "properties" .= eProperties
, if null eEntities then Nothing else Just $ "entities" .= eEntities
...
```

Eight occurrences across `Entity`, `Link`, `Action`, and `Field`. Two spell the
emptiness test differently — `Map.null` for properties, `null` everywhere else —
which is the drift this shape invites, and a ninth field added tomorrow can
quietly encode `[]` instead of omitting the key.

The extraction was written and verified during #160 and held back there: with no
export list on `Data.SirenJSON`, it would have published `omitEmpty` as API on
the way into the 1.0.0.0 commitment. #161 removes that obstacle.

## Scope

- Add the helper:

```haskell
omitEmpty :: (Foldable t, ToJSON (t a)) => Key -> t a -> Maybe Pair
omitEmpty k xs
| null xs = Nothing
| otherwise = Just (k .= xs)
```

- Rewrite the eight call sites in the `Entity`, `Link`, `Action`, and `Field`
instances.
- Drop `null` from the `Data.Map.Strict` import list, which the change makes
redundant — `Foldable` covers `Map` and GHC reports it under
`-Wunused-imports` otherwise.
- Keep the helper out of the export list added by #161.

## Acceptance criteria

- [ ] No `if null … then Nothing else Just …` remains in the encoders.
- [ ] The test suite passes unchanged — this alters no encoding.
- [ ] `cabal build` reports no new warnings.
- [ ] `omitEmpty` is not exported.

## Additional context

Blocked by #161. Measured at +23/−11 on top of #160.

Two neighbouring refactorings were considered and rejected. Collapsing
`InputType`'s two 19-case mappings into one table needs either a `Bounded`
/`Enum` derivation on a public type or a reverse lookup that introduces
partiality, both worse than the duplication. Renaming the `eClass`/`lClass`
/`aClass`/`fClass` field prefixes is a breaking change.

貢獻指南

開啟貢獻指南

評估

這個 Issue 還沒有評估資料。

把新 issue 寄到你的電子郵件信箱

精選適合新手參與的 GitHub issue 摘要。