1717#include " ../src/xsystem.hpp"
1818#include " ../src/xmagics/os.hpp"
1919
20+ #include < iostream>
21+
2022#include < fstream>
2123#if defined(__GNUC__) && !defined(XEUS_CPP_EMSCRIPTEN_WASM_BUILD)
2224 #include < sys/wait.h>
2325 #include < unistd.h>
2426#endif
2527
28+
29+ // / A RAII class to redirect a stream to a stringstream.
30+ // /
31+ // / This class redirects the output of a given std::ostream to a std::stringstream.
32+ // / The original stream is restored when the object is destroyed.
33+ class StreamRedirectRAII {
34+ public:
35+
36+ // / Constructor that starts redirecting the given stream.
37+ StreamRedirectRAII (std::ostream& stream) : old_stream_buff(stream.rdbuf()), stream_to_redirect(stream) {
38+ stream_to_redirect.rdbuf (ss.rdbuf ());
39+ }
40+
41+ // / Destructor that restores the original stream.
42+ ~StreamRedirectRAII () {
43+ stream_to_redirect.rdbuf (old_stream_buff);
44+ }
45+
46+ // / Get the output that was written to the stream.
47+ std::string getCaptured () {
48+ return ss.str ();
49+ }
50+
51+ private:
52+ // / The original buffer of the stream.
53+ std::streambuf* old_stream_buff;
54+
55+ // / The stream that is being redirected.
56+ std::ostream& stream_to_redirect;
57+
58+ // / The stringstream that the stream is redirected to.
59+ std::stringstream ss;
60+ };
61+
2662TEST_SUITE (" execute_request" )
2763{
2864 TEST_CASE (" stl" )
@@ -610,6 +646,20 @@ TEST_SUITE("xmagics_contains"){
610646 }
611647}
612648
649+ class MyMagicLine : public xcpp ::xmagic_line {
650+ public:
651+ virtual void operator ()(const std::string& line) override {
652+ std::cout << line << std::endl;
653+ }
654+ };
655+
656+ class MyMagicCell : public xcpp ::xmagic_cell {
657+ public:
658+ virtual void operator ()(const std::string& line, const std::string& cell) override {
659+ std::cout << line << cell << std::endl;
660+ }
661+ };
662+
613663TEST_SUITE (" xmagics_apply" ){
614664 TEST_CASE (" bad_status_cell" ) {
615665 xcpp::xmagics_manager manager;
@@ -626,6 +676,48 @@ TEST_SUITE("xmagics_apply"){
626676 manager.apply (" %dummy" , kernel_res);
627677 REQUIRE (kernel_res[" status" ] == " error" );
628678 }
679+
680+ TEST_CASE (" good_status_line" ) {
681+
682+ xcpp::xpreamble_manager preamble_manager;
683+
684+ preamble_manager.register_preamble (" magics" , new xcpp::xmagics_manager ());
685+
686+ preamble_manager[" magics" ].get_cast <xcpp::xmagics_manager>().register_magic (" magic2" , MyMagicCell ());
687+
688+ nl::json kernel_res;
689+
690+ preamble_manager[" magics" ].get_cast <xcpp::xmagics_manager>().apply (" %%magic2 qwerty" , kernel_res);
691+
692+ REQUIRE (kernel_res[" status" ] == " ok" );
693+ }
694+
695+ TEST_CASE (" good_status_cell" ) {
696+
697+ xcpp::xpreamble_manager preamble_manager;
698+
699+ preamble_manager.register_preamble (" magics" , new xcpp::xmagics_manager ());
700+
701+ preamble_manager[" magics" ].get_cast <xcpp::xmagics_manager>().register_magic (" magic1" , MyMagicLine ());
702+
703+ nl::json kernel_res;
704+
705+ preamble_manager[" magics" ].get_cast <xcpp::xmagics_manager>().apply (" %magic1 qwerty" , kernel_res);
706+
707+ REQUIRE (kernel_res[" status" ] == " ok" );
708+ }
709+
710+ TEST_CASE (" cell magic with empty cell body" ) {
711+
712+ xcpp::xmagics_manager manager;
713+
714+ StreamRedirectRAII redirect (std::cerr);
715+
716+ manager.apply (" test" , " line" , " " );
717+
718+ REQUIRE (redirect.getCaptured () == " UsageError: %%test is a cell magic, but the cell body is empty.\n "
719+ " If you only intend to display %%test help, please use a double line break to fill in the cell body.\n " );
720+ }
629721}
630722
631723#if defined(__GNUC__) && !defined(XEUS_CPP_EMSCRIPTEN_WASM_BUILD)
0 commit comments