Skip to content

Commit

Permalink
align text blocks
Browse files Browse the repository at this point in the history
  • Loading branch information
barneyb committed Apr 5, 2024
1 parent b66bfd9 commit 36bc77e
Show file tree
Hide file tree
Showing 11 changed files with 148 additions and 123 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,8 @@
order by case :name when uom.name then 1
when uom.pluralName then 2
else 3
end""")
end
""")
public class UnitOfMeasure extends BaseEntity {

public static final Comparator<UnitOfMeasure> BY_NAME = (a, b) -> {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,23 +10,23 @@
public interface PantryItemRepository extends CrudRepository<PantryItem, Long>, PantryItemSearchRepository {

@Query("""
select item
from PantryItem item
left join item.synonyms syn
where upper(item.name) = upper(:name)
or upper(syn) = upper(:name)
order by item.id
""")
select item
from PantryItem item
left join item.synonyms syn
where upper(item.name) = upper(:name)
or upper(syn) = upper(:name)
order by item.id
""")
List<PantryItem> findByNameIgnoreCaseOrderById(String name);

@Query("""
select item
from PantryItem item
left join item.synonyms syn
where upper(item.name) like upper('%' || :name || '%') escape '\\'
or upper(syn) like upper('%' || :name || '%') escape '\\'
order by item.id
""")
select item
from PantryItem item
left join item.synonyms syn
where upper(item.name) like upper('%' || :name || '%') escape '\\'
or upper(syn) like upper('%' || :name || '%') escape '\\'
order by item.id
""")
List<PantryItem> findAllByNameIgnoreCaseContainingOrderById(String name);

List<PantryItem> findAllByUpdatedAtIsAfter(Instant cutoff);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,22 +18,23 @@ public class PantryItemSearchRepositoryImpl implements PantryItemSearchRepositor
public SearchResponse<PantryItem> search(PantryItemSearchRequest request) {
var stmt = new NamedParameterQuery(
"""
select distinct item
from PantryItem item
left join item.synonyms syn
left join item.labels.label lbl
""");
select distinct item
from PantryItem item
left join item.synonyms syn
left join item.labels.label lbl
""");
int i = 0;
for (var word : EnglishUtils.canonicalize(request.getFilter())
.split(" ")) {
if (word.isBlank()) continue;
stmt.append(i == 0 ? "where" : "or");
String p = "p" + (i++);
stmt.append(String.format("""
(upper(item.name) like upper('%%' || :%1$s || '%%') escape '\\'
or upper(syn) like upper('%%' || :%1$s || '%%') escape '\\'
or upper(lbl.name) like upper('%%' || :%1$s || '%%') escape '\\')
""", p), p, word);
stmt.append(String.format(
"""
(upper(item.name) like upper('%%' || :%1$s || '%%') escape '\\'
or upper(syn) like upper('%%' || :%1$s || '%%') escape '\\'
or upper(lbl.name) like upper('%%' || :%1$s || '%%') escape '\\')
""", p), p, word);
}
stmt.append("order by ");
for (var sort : request.getSort()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,15 @@ public interface PlanRepository extends BaseEntityRepository<Plan> {
Iterable<Plan> findByOwner(User owner);

@Query("""
select l
from Plan l
where l.acl.owner.id = ?1
or exists (
select 1
from l.acl.grants gs
where key(gs).id = ?1
)
order by l.name, l.id""")
select l
from Plan l
where l.acl.owner.id = ?1
or exists (
select 1
from l.acl.grants gs
where key(gs).id = ?1
)
order by l.name, l.id""")
Iterable<Plan> findAccessibleLists(Long userId);

@Query("select coalesce(max(position), -1) from Plan where acl.owner = ?1")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -105,11 +105,11 @@ public long countMyUses(PantryItem pantryItem) {
private long countUses(User owner, PantryItem pantryItem) {
var q = new NamedParameterQuery(
"""
select count(distinct r.id)
from Recipe r
join r.ingredients ing
where ing.ingredient.id = :id
""", "id", pantryItem.getId());
select count(distinct r.id)
from Recipe r
join r.ingredients ing
where ing.ingredient.id = :id
""", "id", pantryItem.getId());
if (owner != null) {
q.append(" and r.owner.id = :owner",
"owner",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,11 +24,11 @@ public PantryItem combineItems(PantryItem toKeep, PantryItem other) {
// favorite.object_id // todo: UK violations?!
update(new NamedParameterQuery(
"""
update favorite
set object_id = :toKeep
where object_type = 'PantryItem'
and object_id = :other
""",
update favorite
set object_id = :toKeep
where object_type = 'PantryItem'
and object_id = :other
""",
idMap));
// ingredient_labels.ingredient_id
for (var lbl : other.getLabels()) {
Expand All @@ -37,10 +37,10 @@ public PantryItem combineItems(PantryItem toKeep, PantryItem other) {
// inventory_item.ingredient_id // todo: UK violations?!
update(new NamedParameterQuery(
"""
update inventory_item
set ingredient_id = :toKeep
where ingredient_id = :other
""",
update inventory_item
set ingredient_id = :toKeep
where ingredient_id = :other
""",
idMap));
// pantry_item_synonyms.pantry_item_id
toKeep.addSynonym(other.getName());
Expand All @@ -50,18 +50,18 @@ public PantryItem combineItems(PantryItem toKeep, PantryItem other) {
// plan_item.ingredient_id
update(new NamedParameterQuery(
"""
update plan_item
set ingredient_id = :toKeep
where ingredient_id = :other
""",
update plan_item
set ingredient_id = :toKeep
where ingredient_id = :other
""",
idMap));
// recipe_ingredients.ingredient_id
update(new NamedParameterQuery(
"""
update recipe_ingredients
set ingredient_id = :toKeep
where ingredient_id = :other
""",
update recipe_ingredients
set ingredient_id = :toKeep
where ingredient_id = :other
""",
idMap));
pantryItemRepository.delete(other);
return toKeep;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,12 @@ public class RecipeFulltextIndexer {
@Transactional(propagation = Propagation.REQUIRES_NEW)
public void reindexRecipeImmediately(ReindexRecipeEvent event) {
NamedParameterQuery query = new NamedParameterQuery(
"DELETE\n" +
"FROM recipe_fulltext_reindex_queue\n" +
"WHERE id = :id",
"id",
event.getRecipeId());
"""
DELETE
FROM recipe_fulltext_reindex_queue
WHERE id = :id""",
"id",
event.getRecipeId());
int rowsAffected = jdbcTemplate.update(query.getStatement(),
query.getParameters());
if (rowsAffected == 0) {
Expand All @@ -54,19 +55,19 @@ public void reindexRecipeImmediately(ReindexRecipeEvent event) {
// not @Transactional; they're done imperatively within.
public void reindexQueued() {
NamedParameterQuery query = new NamedParameterQuery(
"DELETE\n" +
"FROM recipe_fulltext_reindex_queue\n" +
"WHERE id IN (SELECT id\n" +
" FROM recipe_fulltext_reindex_queue\n" +
" ORDER BY ts\n" +
" LIMIT :batch_size)",
"batch_size",
BATCH_SIZE);
"DELETE\n" +
"FROM recipe_fulltext_reindex_queue\n" +
"WHERE id IN (SELECT id\n" +
" FROM recipe_fulltext_reindex_queue\n" +
" ORDER BY ts\n" +
" LIMIT :batch_size)",
"batch_size",
BATCH_SIZE);
while (true) {
@SuppressWarnings("DataFlowIssue") // box/unbox shenanigans
int rowsAffected = txTemplate.execute(
tx -> jdbcTemplate.update(query.getStatement(),
query.getParameters()));
tx -> jdbcTemplate.update(query.getStatement(),
query.getParameters()));
if (rowsAffected < BATCH_SIZE) break;
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,10 +29,12 @@ public class RecipeReindexQueueServiceImpl implements RecipeReindexQueueService
public IndexStats getIndexStats() {
IndexStats.IndexStatsBuilder builder = IndexStats.builder();
SqlRowSet rs = jdbcTemplate.queryForRowSet(
"SELECT COUNT(*)\n" +
" , COALESCE(CAST(EXTRACT(EPOCH FROM NOW() - MIN(ts)) AS BIGINT), -1)\n" +
" , COALESCE(CAST(EXTRACT(EPOCH FROM NOW() - MAX(ts)) AS BIGINT), -1)\n" +
"FROM recipe_fulltext_reindex_queue\n",
"""
SELECT COUNT(*)
, COALESCE(CAST(EXTRACT(EPOCH FROM NOW() - MIN(ts)) AS BIGINT), -1)
, COALESCE(CAST(EXTRACT(EPOCH FROM NOW() - MAX(ts)) AS BIGINT), -1)
FROM recipe_fulltext_reindex_queue
""",
Collections.emptyMap());
rs.next();
builder.queueSize(rs.getLong(1))
Expand All @@ -43,10 +45,12 @@ public IndexStats getIndexStats() {
q -> q.append(" AND recipe_fulltext IS NOT NULL\n")));
builder.staleRecipeCount(countRecipes(
q -> q.append(" AND recipe_fulltext IS NOT NULL\n")
.append(" AND EXISTS(SELECT *\n" +
" FROM recipe_fulltext_reindex_queue\n" +
" WHERE id = ingredient.id\n" +
" )\n")));
.append("""
AND EXISTS(SELECT *
FROM recipe_fulltext_reindex_queue
WHERE id = ingredient.id
)
""")));
return builder.build();
}

Expand All @@ -58,9 +62,11 @@ private long countRecipes() {

private long countRecipes(Consumer<NamedParameterQuery> whereAction) {
NamedParameterQuery query = new NamedParameterQuery(
"SELECT COUNT(*) count\n" +
"FROM ingredient\n" +
"WHERE dtype = 'Recipe'\n");
"""
SELECT COUNT(*) count
FROM ingredient
WHERE dtype = 'Recipe'
""");
whereAction.accept(query);
SqlRowSet rs = jdbcTemplate.queryForRowSet(query.getStatement(),
query.getParameters());
Expand All @@ -81,22 +87,26 @@ public void enqueueRecipe(Recipe recipe) {

public void enqueueRecipesWithIngredient(Ingredient ingredient) {
enqueue(query -> query.append(
"SELECT recipe_id\n" +
"FROM recipe_ingredients\n" +
"WHERE ingredient_id = :id\n",
"id",
ingredient.getId()));
"""
SELECT recipe_id
FROM recipe_ingredients
WHERE ingredient_id = :id
""",
"id",
ingredient.getId()));
}

public void enqueueRecipesWithLabel(Label label) {
enqueue(query -> query.append(
"SELECT recipe.id\n" +
"FROM ingredient_labels link\n" +
" JOIN ingredient recipe ON recipe.id = link.ingredient_id\n" +
"WHERE link.label_id = :id\n" +
" AND recipe.dtype = 'Recipe'\n",
"id",
label.getId()));
"""
SELECT recipe.id
FROM ingredient_labels link
JOIN ingredient recipe ON recipe.id = link.ingredient_id
WHERE link.label_id = :id
AND recipe.dtype = 'Recipe'
""",
"id",
label.getId()));
}

@SuppressWarnings("UnusedReturnValue")
Expand Down
18 changes: 12 additions & 6 deletions src/main/java/com/brennaswitzer/cookbook/web/DbController.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,17 @@
import org.springframework.http.HttpStatus;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.bind.annotation.RestController;

import java.util.Map;
import java.util.regex.Pattern;
import java.util.stream.Collectors;

@SuppressWarnings({"SpringJavaAutowiredFieldsWarningInspection", "SqlResolve"})
@SuppressWarnings({ "SpringJavaAutowiredFieldsWarningInspection", "SqlResolve" })
@RestController
@RequestMapping("api/_db")
@PreAuthorize("hasRole('DEVELOPER')")
Expand All @@ -30,10 +34,12 @@ private void validateTableName(String tableName) {
@GetMapping("")
@ResponseStatus(HttpStatus.OK)
public Iterable<Map<String, Object>> getTables() {
return tmpl.queryForList("select table_name\n" +
"from information_schema.tables\n" +
"where table_schema = 'public'\n" +
"order by 1")
return tmpl.queryForList("""
select table_name
from information_schema.tables
where table_schema = 'public'
order by 1
""")
.stream()
.peek(it -> it.put("record_count", tmpl
.queryForObject("select count(*)\n" +
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,14 +10,14 @@ public class PostgresFullTextQueryConverterTest {
@ParameterizedTest
@CsvSource(quoteCharacter = '#', // we want to process single quotes
textBlock = """
chicken , chicken:*
'chicken' , chicken
chicken thighs , chicken:* | thighs:*
'chicken thighs' , chicken <-> thighs
"chicken thighs" , chicken <-> thighs
celery "chicken thighs" , celery:* | chicken <-> thighs
'a b' "c d" e 'f "g , a <-> b | c <-> d | e:* | f:* | g:*
""")
chicken , chicken:*
'chicken' , chicken
chicken thighs , chicken:* | thighs:*
'chicken thighs' , chicken <-> thighs
"chicken thighs" , chicken <-> thighs
celery "chicken thighs" , celery:* | chicken <-> thighs
'a b' "c d" e 'f "g , a <-> b | c <-> d | e:* | f:* | g:*
""")
public void filterConversion(String input, String expected) {
String actual = new PostgresFullTextQueryConverter()
.convert(input);
Expand Down
Loading

0 comments on commit 36bc77e

Please sign in to comment.