@@ -559,17 +559,11 @@ pub(super) fn buffers_remaining_impl(editor: &mut Editor) -> anyhow::Result<()>
559559 Ok(())
560560}
561561
562−fn write_all_impl(
562+pub fn write_all_impl(
563563 cx: &mut compositor::Context,
564− _args: &[Cow<str>],
565− event: PromptEvent,
566− quit: bool,
567564 force: bool,
565+ write_scratch: bool,
568566) -> anyhow::Result<()> {
569− if event != PromptEvent::Validate {
570− return Ok(());
571− }
572−
573567 let mut errors: Vec<&'static str> = Vec::new();
574568 let auto_format = cx.editor.config().auto_format;
575569 let jobs = &mut cx.jobs;
@@ -580,12 +574,13 @@ fn write_all_impl(
580574 .documents
581575 .values()
582576 .filter_map(|doc| {
583− if doc.path().is_none() {
584− errors.push("cannot write a buffer without a filename\n");
577+ if !doc.is_modified() {
585578 return None;
586579 }
587−
588− if !doc.is_modified() {
580+ if doc.path().is_none() {
581+ if write_scratch {
582+ errors.push("cannot write a buffer without a filename\n");
583+ }
589584 return None;
590585 }
591586
@@ -611,20 +606,6 @@ fn write_all_impl(
611606 cx.editor.save::<PathBuf>(id, None, force)?;
612607 }
613608
614− if quit {
615− cx.block_try_flush_writes()?;
616−
617− if !force {
618− buffers_remaining_impl(cx.editor)?;
619− }
620−
621− // close all views
622− let views: Vec<_> = cx.editor.tree.views().map(|(view, _)| view.id).collect();
623− for view_id in views {
624− cx.editor.close(view_id);
625− }
626− }
627−
628609 if !errors.is_empty() && !force {
629610 bail!("{:?}", errors);
630611 }
@@ -634,49 +615,50 @@ fn write_all_impl(
634615
635616fn write_all(
636617 cx: &mut compositor::Context,
637− args: &[Cow<str>],
618+ _args: &[Cow<str>],
638619 event: PromptEvent,
639620) -> anyhow::Result<()> {
640621 if event != PromptEvent::Validate {
641622 return Ok(());
642623 }
643624
644− write_all_impl(cx, args, event, false, false)
625+ write_all_impl(cx, false, true)
645626}
646627
647628fn write_all_quit(
648629 cx: &mut compositor::Context,
649− args: &[Cow<str>],
630+ _args: &[Cow<str>],
650631 event: PromptEvent,
651632) -> anyhow::Result<()> {
652633 if event != PromptEvent::Validate {
653634 return Ok(());
654635 }
655−
656− write_all_impl(cx, args, event, true, false)
636+ write_all_impl(cx, false, true)?;
637+ quit_all_impl(cx, false)
657638}
658639
659640fn force_write_all_quit(
660641 cx: &mut compositor::Context,
661− args: &[Cow<str>],
642+ _args: &[Cow<str>],
662643 event: PromptEvent,
663644) -> anyhow::Result<()> {
664645 if event != PromptEvent::Validate {
665646 return Ok(());
666647 }
667−
668− write_all_impl(cx, args, event, true, true)
648+ let _ = write_all_impl(cx, true, true);
649+ quit_all_impl(cx, true)
669650}
670651
671−fn quit_all_impl(editor: &mut Editor, force: bool) -> anyhow::Result<()> {
652+fn quit_all_impl(cx: &mut compositor::Context, force: bool) -> anyhow::Result<()> {
653+ cx.block_try_flush_writes()?;
672654 if !force {
673− buffers_remaining_impl(editor)?;
655+ buffers_remaining_impl(cx.editor)?;
674656 }
675657
676658 // close all views
677− let views: Vec<_> = editor.tree.views().map(|(view, _)| view.id).collect();
659+ let views: Vec<_> = cx.editor.tree.views().map(|(view, _)| view.id).collect();
678660 for view_id in views {
679− editor.close(view_id);
661+ cx.editor.close(view_id);
680662 }
681663
682664 Ok(())
@@ -691,8 +673,7 @@ fn quit_all(
691673 return Ok(());
692674 }
693675
694− cx.block_try_flush_writes()?;
695− quit_all_impl(cx.editor, false)
676+ quit_all_impl(cx, false)
696677}
697678
698679fn force_quit_all(
@@ -704,7 +685,7 @@ fn force_quit_all(
704685 return Ok(());
705686 }
706687
707− quit_all_impl(cx.editor, true)
688+ quit_all_impl(cx, true)
708689}
709690
710691fn cquit(
@@ -722,8 +703,7 @@ fn cquit(
722703 .unwrap_or(1);
723704
724705 cx.editor.exit_code = exit_code;
725− cx.block_try_flush_writes()?;
726− quit_all_impl(cx.editor, false)
706+ quit_all_impl(cx, false)
727707}
728708
729709fn force_cquit(
@@ -741,7 +721,7 @@ fn force_cquit(
741721 .unwrap_or(1);
742722 cx.editor.exit_code = exit_code;
743723
744− quit_all_impl(cx.editor, true)
724+ quit_all_impl(cx, true)
745725}
746726
747727fn theme(
@@ -2141,7 +2121,7 @@ pub static TYPABLE_COMMAND_MAP: Lazy<HashMap<&'static str, &'static TypableComma
21412121 .collect()
21422122 });
21432123
2144−pub fn command_mode(cx: &mut Context) {
2124+pub(super) fn command_mode(cx: &mut Context) {
21452125 let mut prompt = Prompt::new(
21462126 ":".into(),
21472127 Some(':'),