feat(buscar): add discovery landing state, filter pills, counter, and sort
This commit is contained in:
@@ -0,0 +1,101 @@
|
||||
import 'package:flutter_test/flutter_test.dart';
|
||||
import 'package:pluriwave/estado/orden_emisoras.dart';
|
||||
import 'package:pluriwave/modelos/emisora.dart';
|
||||
|
||||
/// WU6: every criterion the Buscar "Ordenar" control can render must map to
|
||||
/// a real, tested [OrdenEmisoras] case (`station-discovery-browse` spec,
|
||||
/// "Client-Side Search Sort Only" — "the system MUST NOT render an option
|
||||
/// that does not actually sort").
|
||||
void main() {
|
||||
Emisora conMetricas({
|
||||
required String uuid,
|
||||
required String nombre,
|
||||
int? bitrate,
|
||||
int votes = 0,
|
||||
int clickcount = 0,
|
||||
}) => Emisora(
|
||||
uuid: uuid,
|
||||
nombre: nombre,
|
||||
url: 'https://stream.demo/$uuid',
|
||||
bitrate: bitrate,
|
||||
votes: votes,
|
||||
clickcount: clickcount,
|
||||
);
|
||||
|
||||
group('OrdenEmisoras.nombre', () {
|
||||
test('ordena alfabéticamente sin distinguir mayúsculas', () {
|
||||
final emisoras = [
|
||||
conMetricas(uuid: 'z', nombre: 'zeta fm'),
|
||||
conMetricas(uuid: 'a', nombre: 'Alfa FM'),
|
||||
conMetricas(uuid: 'm', nombre: 'medio fm'),
|
||||
];
|
||||
|
||||
final resultado = ordenarEmisoras(emisoras, OrdenEmisoras.nombre);
|
||||
|
||||
expect(resultado.map((e) => e.uuid), ['a', 'm', 'z']);
|
||||
});
|
||||
});
|
||||
|
||||
group('OrdenEmisoras.calidad', () {
|
||||
test('ordena por bitrate descendente', () {
|
||||
final emisoras = [
|
||||
conMetricas(uuid: 'baja', nombre: 'Baja', bitrate: 64),
|
||||
conMetricas(uuid: 'alta', nombre: 'Alta', bitrate: 320),
|
||||
conMetricas(uuid: 'media', nombre: 'Media', bitrate: 128),
|
||||
];
|
||||
|
||||
final resultado = ordenarEmisoras(emisoras, OrdenEmisoras.calidad);
|
||||
|
||||
expect(resultado.map((e) => e.uuid), ['alta', 'media', 'baja']);
|
||||
});
|
||||
});
|
||||
|
||||
group('OrdenEmisoras.popularidad', () {
|
||||
test('ordena por votos descendente', () {
|
||||
final emisoras = [
|
||||
conMetricas(uuid: 'pocos', nombre: 'Pocos', votes: 3),
|
||||
conMetricas(uuid: 'muchos', nombre: 'Muchos', votes: 900),
|
||||
conMetricas(uuid: 'medio', nombre: 'Medio', votes: 40),
|
||||
];
|
||||
|
||||
final resultado = ordenarEmisoras(emisoras, OrdenEmisoras.popularidad);
|
||||
|
||||
expect(resultado.map((e) => e.uuid), ['muchos', 'medio', 'pocos']);
|
||||
});
|
||||
|
||||
test('en empate de votos, desempata por clickcount descendente', () {
|
||||
final emisoras = [
|
||||
conMetricas(
|
||||
uuid: 'menos-clicks',
|
||||
nombre: 'Menos clicks',
|
||||
votes: 10,
|
||||
clickcount: 5,
|
||||
),
|
||||
conMetricas(
|
||||
uuid: 'mas-clicks',
|
||||
nombre: 'Mas clicks',
|
||||
votes: 10,
|
||||
clickcount: 500,
|
||||
),
|
||||
];
|
||||
|
||||
final resultado = ordenarEmisoras(emisoras, OrdenEmisoras.popularidad);
|
||||
|
||||
expect(resultado.map((e) => e.uuid), ['mas-clicks', 'menos-clicks']);
|
||||
});
|
||||
});
|
||||
|
||||
test(
|
||||
'todos los valores del enum tienen un caso de ordenamiento implementado '
|
||||
'(regresión: nunca ofrecer una opción decorativa que no ordene)',
|
||||
() {
|
||||
for (final criterio in OrdenEmisoras.values) {
|
||||
// Must not throw and must return a same-length list for every case.
|
||||
final resultado = ordenarEmisoras([
|
||||
conMetricas(uuid: 'x', nombre: 'X'),
|
||||
], criterio);
|
||||
expect(resultado, hasLength(1));
|
||||
}
|
||||
},
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user