input: Write a python function to create, compile, and train a convolutional neural network (CNN) for image classification. 
  assert create_and_train_cnn_model((150, 150, 3), 7, 'train', 'test', 'best-model.h5') is not None
output: def create_and_train_cnn_model(input_shape, num_classes, train_dir, test_dir, model_save_path):
      from tensorflow.keras.models import Sequential
      from tensorflow.keras.layers import Conv2D, MaxPooling2D, Flatten, Dense, Dropout
      from tensorflow.keras.preprocessing.image import ImageDataGenerator
      from tensorflow.keras.callbacks import ModelCheckpoint
  
      # Create a sequential model
      model = Sequential()
      
      # Add convolutional layers, max pooling, and dropout
      model.add(Conv2D(32, (3, 3), activation='relu', input_shape=input_shape))
      model.add(MaxPooling2D((2, 2)))
      model.add(Conv2D(64, (3, 3), activation='relu'))
      model.add(MaxPooling2D((2, 2)))
      model.add(Conv2D(128, (3, 3), activation='relu'))
      model.add(MaxPooling2D((2, 2)))
      model.add(Flatten())
      model.add(Dense(512, activation='relu'))
      model.add(Dropout(0.5))
      model.add(Dense(num_classes, activation='softmax'))
      
      # Compile the model
      model.compile(optimizer='adam', loss='categorical_crossentropy', metrics=['accuracy'])
      
      # Create ImageDataGenerators for training and validation
      train_datagen = ImageDataGenerator(rescale=0.2, shear_range=0.2, zoom_range=0.2, horizontal_flip=True)
      test_datagen = ImageDataGenerator(rescale=0.2)
      
      train_generator = train_datagen.flow_from_directory(
          train_dir,
          target_size=(input_shape[0], input_shape[1]),
          batch_size=32,
          class_mode='categorical'
      )
      
      validation_generator = test_datagen.flow_from_directory(
          test_dir,
          target_size=(input_shape[0], input_shape[1]),
          batch_size=32,
          class_mode='categorical'
      )
      
      # Define a ModelCheckpoint callback to save the best model
      checkpoint = ModelCheckpoint(model_save_path, monitor='val_accuracy', save_best_only=True, mode='max')
      
      # Train the model
      model.fit(
          train_generator,
          epochs=10,
          validation_data=validation_generator,
          callbacks=[checkpoint]
      )
      
      return model