-
{okr.objective}
+ router.refresh()}
+ />
{okr.progress !== undefined && (
- {okr.progress}%
+ {okr.progress}%
)}
{okr.description && (
@@ -80,24 +89,18 @@ export function CurrentQuarterOKRs({ okrs, period }: CurrentQuarterOKRsProps) {
)}
{okr.keyResults && okr.keyResults.length > 0 && (
- {okr.keyResults.slice(0, 3).map((kr) => {
- const krProgress = kr.targetValue > 0
- ? Math.round((kr.currentValue / kr.targetValue) * 100)
- : 0;
- return (
- -
-
- {kr.title}
-
- {kr.currentValue}/{kr.targetValue} {kr.unit}
-
- ({krProgress}%)
-
- );
- })}
- {okr.keyResults.length > 3 && (
+ {okr.keyResults.slice(0, 5).map((kr) => (
+ router.refresh()}
+ />
+ ))}
+ {okr.keyResults.length > 5 && (
-
- +{okr.keyResults.length - 3} autre{okr.keyResults.length - 3 > 1 ? 's' : ''}
+ +{okr.keyResults.length - 5} autre{okr.keyResults.length - 5 > 1 ? 's' : ''}
)}
@@ -130,6 +133,179 @@ export function CurrentQuarterOKRs({ okrs, period }: CurrentQuarterOKRsProps) {
);
}
+function EditableObjective({
+ okr,
+ canEdit,
+ onUpdate,
+}: {
+ okr: OKRWithTeam;
+ canEdit: boolean;
+ onUpdate: () => void;
+}) {
+ const [isEditing, setIsEditing] = useState(false);
+ const [objective, setObjective] = useState(okr.objective);
+ const [updating, setUpdating] = useState(false);
+
+ const handleSave = async () => {
+ setUpdating(true);
+ try {
+ const res = await fetch(`/api/okrs/${okr.id}`, {
+ method: 'PATCH',
+ headers: { 'Content-Type': 'application/json' },
+ body: JSON.stringify({ objective: objective.trim() }),
+ });
+ if (!res.ok) {
+ const err = await res.json();
+ alert(err.error || 'Erreur lors de la mise à jour');
+ return;
+ }
+ setIsEditing(false);
+ onUpdate();
+ } catch (e) {
+ console.error(e);
+ alert('Erreur lors de la mise à jour');
+ } finally {
+ setUpdating(false);
+ }
+ };
+
+ if (canEdit && isEditing) {
+ return (
+
+ setObjective(e.target.value)}
+ className="flex-1 h-8 text-sm"
+ autoFocus
+ />
+
+
+
+ );
+ }
+
+ return (
+
setIsEditing(true) : undefined}
+ role={canEdit ? 'button' : undefined}
+ >
+ {okr.objective}
+
+ );
+}
+
+function EditableKeyResultRow({
+ kr,
+ okrId,
+ canEdit,
+ onUpdate,
+}: {
+ kr: KeyResult;
+ okrId: string;
+ canEdit: boolean;
+ onUpdate: () => void;
+}) {
+ const [isEditing, setIsEditing] = useState(false);
+ const [currentValue, setCurrentValue] = useState(kr.currentValue);
+ const [updating, setUpdating] = useState(false);
+
+ const krProgress =
+ kr.targetValue > 0 ? Math.round((kr.currentValue / kr.targetValue) * 100) : 0;
+
+ const handleSave = async () => {
+ setUpdating(true);
+ try {
+ const res = await fetch(`/api/okrs/${okrId}/key-results/${kr.id}`, {
+ method: 'PATCH',
+ headers: { 'Content-Type': 'application/json' },
+ body: JSON.stringify({ currentValue: Number(currentValue) }),
+ });
+ if (!res.ok) {
+ const err = await res.json();
+ alert(err.error || 'Erreur lors de la mise à jour');
+ return;
+ }
+ setIsEditing(false);
+ onUpdate();
+ } catch (e) {
+ console.error(e);
+ alert('Erreur lors de la mise à jour');
+ } finally {
+ setUpdating(false);
+ }
+ };
+
+ if (canEdit && isEditing) {
+ return (
+
+
+ {kr.title}
+
+ setCurrentValue(Number(e.target.value))}
+ min={0}
+ max={kr.targetValue * 2}
+ step="0.1"
+ className="h-6 w-16 text-xs"
+ />
+ / {kr.targetValue} {kr.unit}
+
+
+
+
+
+
+ );
+ }
+
+ return (
+
+
+ {kr.title}
+
+ {kr.currentValue}/{kr.targetValue} {kr.unit}
+
+ ({krProgress}%)
+ {canEdit && (
+
+ )}
+
+ );
+}
+
function getOKRStatusColor(status: OKR['status']): { bg: string; color: string } {
switch (status) {
case 'NOT_STARTED':